@dxos/react-ui-editor 0.8.2-main.fbd8ed0 → 0.8.2-staging.4d6ad0f
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/lib/browser/index.mjs +1731 -926
- package/dist/lib/browser/index.mjs.map +4 -4
- package/dist/lib/browser/meta.json +1 -1
- package/dist/lib/browser/testing/index.mjs +3 -64
- package/dist/lib/browser/testing/index.mjs.map +4 -4
- package/dist/lib/node/index.cjs +1912 -1111
- package/dist/lib/node/index.cjs.map +4 -4
- package/dist/lib/node/meta.json +1 -1
- package/dist/lib/node/testing/index.cjs +3 -75
- package/dist/lib/node/testing/index.cjs.map +4 -4
- package/dist/lib/node-esm/index.mjs +1731 -926
- package/dist/lib/node-esm/index.mjs.map +4 -4
- package/dist/lib/node-esm/meta.json +1 -1
- package/dist/lib/node-esm/testing/index.mjs +3 -64
- package/dist/lib/node-esm/testing/index.mjs.map +4 -4
- package/dist/types/src/components/EditorToolbar/EditorToolbar.d.ts.map +1 -1
- package/dist/types/src/components/EditorToolbar/index.d.ts +1 -1
- package/dist/types/src/components/EditorToolbar/index.d.ts.map +1 -1
- package/dist/types/src/components/EditorToolbar/util.d.ts +4 -6
- package/dist/types/src/components/EditorToolbar/util.d.ts.map +1 -1
- package/dist/types/src/components/Popover/RefDropdownMenu.d.ts +21 -0
- package/dist/types/src/components/Popover/RefDropdownMenu.d.ts.map +1 -0
- package/dist/types/src/{testing → components/Popover}/RefPopover.d.ts +1 -1
- package/dist/types/src/components/Popover/RefPopover.d.ts.map +1 -0
- package/dist/types/src/components/Popover/index.d.ts +3 -0
- package/dist/types/src/components/Popover/index.d.ts.map +1 -0
- package/dist/types/src/components/index.d.ts +1 -0
- package/dist/types/src/components/index.d.ts.map +1 -1
- package/dist/types/src/defaults.d.ts +2 -5
- package/dist/types/src/defaults.d.ts.map +1 -1
- package/dist/types/src/extensions/annotations.d.ts +4 -1
- package/dist/types/src/extensions/annotations.d.ts.map +1 -1
- package/dist/types/src/extensions/autocomplete.d.ts +1 -2
- package/dist/types/src/extensions/autocomplete.d.ts.map +1 -1
- package/dist/types/src/extensions/automerge/automerge.stories.d.ts.map +1 -1
- package/dist/types/src/extensions/automerge/sync.d.ts.map +1 -1
- package/dist/types/src/extensions/awareness/awareness-provider.d.ts.map +1 -1
- package/dist/types/src/extensions/awareness/awareness.d.ts.map +1 -1
- package/dist/types/src/extensions/command/command.d.ts +1 -2
- package/dist/types/src/extensions/command/command.d.ts.map +1 -1
- package/dist/types/src/extensions/command/hint.d.ts +14 -2
- package/dist/types/src/extensions/command/hint.d.ts.map +1 -1
- package/dist/types/src/extensions/command/index.d.ts +2 -0
- package/dist/types/src/extensions/command/index.d.ts.map +1 -1
- package/dist/types/src/extensions/command/menu.d.ts +7 -8
- package/dist/types/src/extensions/command/menu.d.ts.map +1 -1
- package/dist/types/src/extensions/command/state.d.ts +1 -1
- package/dist/types/src/extensions/command/state.d.ts.map +1 -1
- package/dist/types/src/extensions/command/typeahead.d.ts +17 -0
- package/dist/types/src/extensions/command/typeahead.d.ts.map +1 -0
- package/dist/types/src/extensions/comments.d.ts +2 -12
- package/dist/types/src/extensions/comments.d.ts.map +1 -1
- package/dist/types/src/extensions/factories.d.ts +4 -0
- package/dist/types/src/extensions/factories.d.ts.map +1 -1
- package/dist/types/src/extensions/index.d.ts +2 -0
- package/dist/types/src/extensions/index.d.ts.map +1 -1
- package/dist/types/src/extensions/json.d.ts +7 -0
- package/dist/types/src/extensions/json.d.ts.map +1 -0
- package/dist/types/src/extensions/markdown/{editorAction.d.ts → action.d.ts} +1 -1
- package/dist/types/src/extensions/markdown/action.d.ts.map +1 -0
- package/dist/types/src/extensions/markdown/bundle.d.ts +2 -1
- package/dist/types/src/extensions/markdown/bundle.d.ts.map +1 -1
- package/dist/types/src/extensions/markdown/index.d.ts +1 -2
- package/dist/types/src/extensions/markdown/index.d.ts.map +1 -1
- package/dist/types/src/extensions/markdown/styles.d.ts.map +1 -1
- package/dist/types/src/extensions/outliner/commands.d.ts +9 -0
- package/dist/types/src/extensions/outliner/commands.d.ts.map +1 -0
- package/dist/types/src/extensions/outliner/editor.d.ts +5 -0
- package/dist/types/src/extensions/outliner/editor.d.ts.map +1 -0
- package/dist/types/src/extensions/outliner/editor.test.d.ts +2 -0
- package/dist/types/src/extensions/outliner/editor.test.d.ts.map +1 -0
- package/dist/types/src/extensions/outliner/index.d.ts +3 -0
- package/dist/types/src/extensions/outliner/index.d.ts.map +1 -0
- package/dist/types/src/extensions/outliner/outliner.d.ts +10 -0
- package/dist/types/src/extensions/outliner/outliner.d.ts.map +1 -0
- package/dist/types/src/extensions/outliner/outliner.test.d.ts +2 -0
- package/dist/types/src/extensions/outliner/outliner.test.d.ts.map +1 -0
- package/dist/types/src/extensions/outliner/selection.d.ts +12 -0
- package/dist/types/src/extensions/outliner/selection.d.ts.map +1 -0
- package/dist/types/src/extensions/outliner/tree.d.ts +79 -0
- package/dist/types/src/extensions/outliner/tree.d.ts.map +1 -0
- package/dist/types/src/extensions/outliner/tree.test.d.ts +2 -0
- package/dist/types/src/extensions/outliner/tree.test.d.ts.map +1 -0
- package/dist/types/src/stories/Command.stories.d.ts +7 -0
- package/dist/types/src/stories/Command.stories.d.ts.map +1 -0
- package/dist/types/src/stories/{TextEditorComments.stories.d.ts → Comments.stories.d.ts} +3 -3
- package/dist/types/src/stories/Comments.stories.d.ts.map +1 -0
- package/dist/types/src/stories/EditorToolbar.stories.d.ts +12 -0
- package/dist/types/src/stories/EditorToolbar.stories.d.ts.map +1 -0
- package/dist/types/src/stories/{TextEditorSpecial.stories.d.ts → Experimental.stories.d.ts} +3 -6
- package/dist/types/src/stories/Experimental.stories.d.ts.map +1 -0
- package/dist/types/src/stories/Markdown.stories.d.ts +46 -0
- package/dist/types/src/stories/Markdown.stories.d.ts.map +1 -0
- package/dist/types/src/stories/Outliner.stories.d.ts +26 -0
- package/dist/types/src/stories/Outliner.stories.d.ts.map +1 -0
- package/dist/types/src/stories/Preview.stories.d.ts +10 -0
- package/dist/types/src/stories/Preview.stories.d.ts.map +1 -0
- package/dist/types/src/stories/{TextEditorBasic.stories.d.ts → TextEditor.stories.d.ts} +9 -39
- package/dist/types/src/stories/TextEditor.stories.d.ts.map +1 -0
- package/dist/types/src/stories/{story-utils.d.ts → util.d.ts} +6 -6
- package/dist/types/src/stories/util.d.ts.map +1 -0
- package/dist/types/src/styles/theme.d.ts.map +1 -1
- package/dist/types/src/styles/tokens.d.ts.map +1 -1
- package/dist/types/src/testing/index.d.ts +1 -1
- package/dist/types/src/testing/index.d.ts.map +1 -1
- package/dist/types/src/testing/util.d.ts +2 -0
- package/dist/types/src/testing/util.d.ts.map +1 -0
- package/package.json +40 -34
- package/src/components/EditorToolbar/EditorToolbar.tsx +81 -57
- package/src/components/EditorToolbar/index.ts +7 -1
- package/src/components/EditorToolbar/util.ts +3 -4
- package/src/components/Popover/RefDropdownMenu.tsx +77 -0
- package/src/{testing → components/Popover}/RefPopover.tsx +5 -4
- package/src/components/Popover/index.ts +6 -0
- package/src/components/index.ts +1 -0
- package/src/defaults.ts +10 -13
- package/src/extensions/annotations.ts +41 -64
- package/src/extensions/autocomplete.ts +5 -6
- package/src/extensions/automerge/automerge.stories.tsx +2 -7
- package/src/extensions/automerge/automerge.test.tsx +3 -2
- package/src/extensions/automerge/sync.ts +3 -3
- package/src/extensions/awareness/awareness-provider.ts +4 -4
- package/src/extensions/awareness/awareness.ts +7 -7
- package/src/extensions/blast.ts +9 -9
- package/src/extensions/command/command.ts +1 -3
- package/src/extensions/command/hint.ts +7 -7
- package/src/extensions/command/index.ts +2 -0
- package/src/extensions/command/menu.ts +43 -49
- package/src/extensions/command/typeahead.ts +116 -0
- package/src/extensions/comments.ts +4 -69
- package/src/extensions/factories.ts +13 -0
- package/src/extensions/index.ts +2 -0
- package/src/extensions/json.ts +56 -0
- package/src/extensions/markdown/bundle.ts +13 -9
- package/src/extensions/markdown/decorate.ts +7 -7
- package/src/extensions/markdown/image.ts +2 -2
- package/src/extensions/markdown/index.ts +1 -2
- package/src/extensions/markdown/styles.ts +2 -1
- package/src/extensions/markdown/table.ts +3 -3
- package/src/extensions/outliner/commands.ts +242 -0
- package/src/extensions/outliner/editor.test.ts +33 -0
- package/src/extensions/outliner/editor.ts +180 -0
- package/src/extensions/outliner/index.ts +6 -0
- package/src/extensions/outliner/outliner.test.ts +99 -0
- package/src/extensions/outliner/outliner.ts +162 -0
- package/src/extensions/outliner/selection.ts +50 -0
- package/src/extensions/outliner/tree.test.ts +164 -0
- package/src/extensions/outliner/tree.ts +315 -0
- package/src/extensions/preview/preview.ts +5 -5
- package/src/stories/Command.stories.tsx +97 -0
- package/src/stories/{TextEditorComments.stories.tsx → Comments.stories.tsx} +13 -14
- package/src/{components/EditorToolbar → stories}/EditorToolbar.stories.tsx +26 -20
- package/src/stories/{TextEditorSpecial.stories.tsx → Experimental.stories.tsx} +9 -30
- package/src/stories/Markdown.stories.tsx +121 -0
- package/src/stories/Outliner.stories.tsx +108 -0
- package/src/stories/{TextEditorPreview.stories.tsx → Preview.stories.tsx} +46 -136
- package/src/stories/TextEditor.stories.tsx +256 -0
- package/src/stories/{story-utils.tsx → util.tsx} +21 -22
- package/src/styles/theme.ts +12 -5
- package/src/styles/tokens.ts +1 -2
- package/src/testing/index.ts +1 -1
- package/src/testing/util.ts +5 -0
- package/dist/types/src/components/EditorToolbar/EditorToolbar.stories.d.ts +0 -53
- package/dist/types/src/components/EditorToolbar/EditorToolbar.stories.d.ts.map +0 -1
- package/dist/types/src/components/EditorToolbar/comment.d.ts +0 -18
- package/dist/types/src/components/EditorToolbar/comment.d.ts.map +0 -1
- package/dist/types/src/extensions/markdown/editorAction.d.ts.map +0 -1
- package/dist/types/src/extensions/markdown/outliner.d.ts +0 -12
- package/dist/types/src/extensions/markdown/outliner.d.ts.map +0 -1
- package/dist/types/src/stories/TextEditorBasic.stories.d.ts.map +0 -1
- package/dist/types/src/stories/TextEditorComments.stories.d.ts.map +0 -1
- package/dist/types/src/stories/TextEditorPreview.stories.d.ts +0 -13
- package/dist/types/src/stories/TextEditorPreview.stories.d.ts.map +0 -1
- package/dist/types/src/stories/TextEditorSpecial.stories.d.ts.map +0 -1
- package/dist/types/src/stories/story-utils.d.ts.map +0 -1
- package/dist/types/src/testing/RefPopover.d.ts.map +0 -1
- package/src/components/EditorToolbar/comment.ts +0 -30
- package/src/extensions/markdown/outliner.ts +0 -235
- package/src/stories/TextEditorBasic.stories.tsx +0 -333
- /package/src/extensions/markdown/{editorAction.ts → action.ts} +0 -0
@@ -35,12 +35,15 @@ var translations_default = [
|
|
35
35
|
|
36
36
|
// packages/ui/react-ui-editor/src/index.ts
|
37
37
|
import { EditorState as EditorState4 } from "@codemirror/state";
|
38
|
-
import { EditorView as EditorView23, keymap as
|
38
|
+
import { EditorView as EditorView23, keymap as keymap13 } from "@codemirror/view";
|
39
39
|
import { tags as tags2 } from "@lezer/highlight";
|
40
40
|
import { TextKind } from "@dxos/protocols/proto/dxos/echo/model/text";
|
41
41
|
|
42
42
|
// packages/ui/react-ui-editor/src/components/EditorToolbar/EditorToolbar.tsx
|
43
|
-
import
|
43
|
+
import { useSignals as _useSignals } from "@preact-signals/safe-react/tracking";
|
44
|
+
import { Rx } from "@effect-rx/rx-react";
|
45
|
+
import React3, { memo, useMemo as useMemo3 } from "react";
|
46
|
+
import { rxFromSignal } from "@dxos/app-graph";
|
44
47
|
import { ElevationProvider } from "@dxos/react-ui";
|
45
48
|
import { MenuProvider, ToolbarMenu, createGapSeparator, useMenuActions } from "@dxos/react-ui-menu";
|
46
49
|
import { textBlockWidth } from "@dxos/react-ui-theme";
|
@@ -71,233 +74,51 @@ var createEditorActionGroup = (id, props, icon) => createMenuItemGroup(id, {
|
|
71
74
|
});
|
72
75
|
|
73
76
|
// packages/ui/react-ui-editor/src/extensions/annotations.ts
|
74
|
-
import {
|
75
|
-
import { Decoration, EditorView } from "@codemirror/view";
|
76
|
-
import { isNotFalsy } from "@dxos/util";
|
77
|
-
|
78
|
-
// packages/ui/react-ui-editor/src/util/facet.ts
|
79
|
-
import { Facet } from "@codemirror/state";
|
80
|
-
var singleValueFacet = (defaultValue) => Facet.define({
|
81
|
-
// Called immediately.
|
82
|
-
combine: (providers) => {
|
83
|
-
return providers[0] ?? defaultValue;
|
84
|
-
}
|
85
|
-
});
|
86
|
-
|
87
|
-
// packages/ui/react-ui-editor/src/util/cursor.ts
|
88
|
-
var overlap = (a, b) => a.from <= b.to && a.to >= b.from;
|
89
|
-
var defaultCursorConverter = {
|
90
|
-
toCursor: (position) => position.toString(),
|
91
|
-
fromCursor: (cursor) => parseInt(cursor)
|
92
|
-
};
|
93
|
-
var Cursor = class _Cursor {
|
94
|
-
static {
|
95
|
-
this.converter = singleValueFacet(defaultCursorConverter);
|
96
|
-
}
|
97
|
-
static {
|
98
|
-
this.getCursorFromRange = (state, range) => {
|
99
|
-
const cursorConverter2 = state.facet(_Cursor.converter);
|
100
|
-
const from = cursorConverter2.toCursor(range.from);
|
101
|
-
const to = cursorConverter2.toCursor(range.to, -1);
|
102
|
-
return [
|
103
|
-
from,
|
104
|
-
to
|
105
|
-
].join(":");
|
106
|
-
};
|
107
|
-
}
|
108
|
-
static {
|
109
|
-
this.getRangeFromCursor = (state, cursor) => {
|
110
|
-
const cursorConverter2 = state.facet(_Cursor.converter);
|
111
|
-
const parts = cursor.split(":");
|
112
|
-
const from = cursorConverter2.fromCursor(parts[0]);
|
113
|
-
const to = cursorConverter2.fromCursor(parts[1]);
|
114
|
-
return from !== void 0 && to !== void 0 ? {
|
115
|
-
from,
|
116
|
-
to
|
117
|
-
} : void 0;
|
118
|
-
};
|
119
|
-
}
|
120
|
-
};
|
121
|
-
|
122
|
-
// packages/ui/react-ui-editor/src/util/debug.ts
|
123
|
-
import { log } from "@dxos/log";
|
124
|
-
var __dxlog_file = "/home/runner/work/dxos/dxos/packages/ui/react-ui-editor/src/util/debug.ts";
|
125
|
-
var wrapWithCatch = (fn) => {
|
126
|
-
return (...args) => {
|
127
|
-
try {
|
128
|
-
return fn(...args);
|
129
|
-
} catch (err) {
|
130
|
-
log.catch(err, void 0, {
|
131
|
-
F: __dxlog_file,
|
132
|
-
L: 15,
|
133
|
-
S: void 0,
|
134
|
-
C: (f, a) => f(...a)
|
135
|
-
});
|
136
|
-
}
|
137
|
-
};
|
138
|
-
};
|
139
|
-
var callbackWrapper = (fn) => (...args) => {
|
140
|
-
try {
|
141
|
-
return fn(...args);
|
142
|
-
} catch (err) {
|
143
|
-
log.catch(err, void 0, {
|
144
|
-
F: __dxlog_file,
|
145
|
-
L: 29,
|
146
|
-
S: void 0,
|
147
|
-
C: (f, a) => f(...a)
|
148
|
-
});
|
149
|
-
}
|
150
|
-
};
|
151
|
-
var debugDispatcher = (trs, view) => {
|
152
|
-
logChanges(trs);
|
153
|
-
view.update(trs);
|
154
|
-
};
|
155
|
-
var logChanges = (trs) => {
|
156
|
-
const changes = trs.flatMap((tr) => {
|
157
|
-
if (tr.changes.empty) {
|
158
|
-
return void 0;
|
159
|
-
}
|
160
|
-
const changes2 = [];
|
161
|
-
tr.changes.iterChanges((fromA, toA, fromB, toB, inserted) => changes2.push(JSON.stringify({
|
162
|
-
fromA,
|
163
|
-
toA,
|
164
|
-
fromB,
|
165
|
-
toB,
|
166
|
-
inserted: inserted.toString()
|
167
|
-
})));
|
168
|
-
return changes2;
|
169
|
-
}).filter(Boolean);
|
170
|
-
if (changes.length) {
|
171
|
-
log("changes", {
|
172
|
-
changes
|
173
|
-
}, {
|
174
|
-
F: __dxlog_file,
|
175
|
-
L: 62,
|
176
|
-
S: void 0,
|
177
|
-
C: (f, a) => f(...a)
|
178
|
-
});
|
179
|
-
}
|
180
|
-
};
|
181
|
-
|
182
|
-
// packages/ui/react-ui-editor/src/util/dom.ts
|
183
|
-
var flattenRect = (rect, left) => {
|
184
|
-
const x = left ? rect.left : rect.right;
|
185
|
-
return {
|
186
|
-
left: x,
|
187
|
-
right: x,
|
188
|
-
top: rect.top,
|
189
|
-
bottom: rect.bottom
|
190
|
-
};
|
191
|
-
};
|
192
|
-
var scratchRange;
|
193
|
-
var textRange = (node, from, to = from) => {
|
194
|
-
const range = scratchRange || (scratchRange = document.createRange());
|
195
|
-
range.setEnd(node, to);
|
196
|
-
range.setStart(node, from);
|
197
|
-
return range;
|
198
|
-
};
|
199
|
-
var clientRectsFor = (dom) => {
|
200
|
-
if (dom.nodeType === 3) {
|
201
|
-
return textRange(dom, 0, dom.nodeValue.length).getClientRects();
|
202
|
-
} else if (dom.nodeType === 1) {
|
203
|
-
return dom.getClientRects();
|
204
|
-
} else {
|
205
|
-
return [];
|
206
|
-
}
|
207
|
-
};
|
208
|
-
|
209
|
-
// packages/ui/react-ui-editor/src/util/react.tsx
|
210
|
-
import React from "react";
|
211
|
-
import { createRoot } from "react-dom/client";
|
212
|
-
import { ThemeProvider, Tooltip } from "@dxos/react-ui";
|
213
|
-
import { defaultTx } from "@dxos/react-ui-theme";
|
214
|
-
var createElement = (tag, options, children) => {
|
215
|
-
const el = document.createElement(tag);
|
216
|
-
if (options?.className) {
|
217
|
-
el.className = options.className;
|
218
|
-
}
|
219
|
-
if (children) {
|
220
|
-
el.append(...Array.isArray(children) ? children : [
|
221
|
-
children
|
222
|
-
]);
|
223
|
-
}
|
224
|
-
return el;
|
225
|
-
};
|
226
|
-
var renderRoot = (root, node) => {
|
227
|
-
createRoot(root).render(/* @__PURE__ */ React.createElement(ThemeProvider, {
|
228
|
-
tx: defaultTx
|
229
|
-
}, node));
|
230
|
-
return root;
|
231
|
-
};
|
232
|
-
var createRenderer = (Component) => (el, props) => {
|
233
|
-
renderRoot(el, /* @__PURE__ */ React.createElement(ThemeProvider, {
|
234
|
-
tx: defaultTx
|
235
|
-
}, /* @__PURE__ */ React.createElement(Tooltip.Provider, null, /* @__PURE__ */ React.createElement(Component, props))));
|
236
|
-
};
|
237
|
-
|
238
|
-
// packages/ui/react-ui-editor/src/extensions/annotations.ts
|
77
|
+
import { RangeSetBuilder } from "@codemirror/state";
|
78
|
+
import { Decoration, EditorView, ViewPlugin } from "@codemirror/view";
|
239
79
|
var annotationMark = Decoration.mark({
|
240
80
|
class: "cm-annotation"
|
241
81
|
});
|
242
|
-
var annotations = (
|
243
|
-
|
244
|
-
|
245
|
-
|
246
|
-
|
247
|
-
const matches = text.matchAll(options.match);
|
248
|
-
for (const match2 of matches) {
|
249
|
-
const from = match2.index;
|
250
|
-
const to = from + match2[0].length;
|
251
|
-
const cursor = Cursor.getCursorFromRange(state, {
|
252
|
-
from,
|
253
|
-
to
|
254
|
-
});
|
255
|
-
annotations2.push({
|
256
|
-
cursor
|
257
|
-
});
|
82
|
+
var annotations = ({ match } = {}) => {
|
83
|
+
return [
|
84
|
+
ViewPlugin.fromClass(class {
|
85
|
+
constructor() {
|
86
|
+
this.decorations = Decoration.none;
|
258
87
|
}
|
259
|
-
|
260
|
-
|
261
|
-
|
262
|
-
|
263
|
-
|
264
|
-
|
265
|
-
|
266
|
-
|
267
|
-
|
268
|
-
|
88
|
+
update(update2) {
|
89
|
+
const builder = new RangeSetBuilder();
|
90
|
+
if (match) {
|
91
|
+
const { from, to } = update2.view.viewport;
|
92
|
+
const text = update2.state.doc.sliceString(from, to);
|
93
|
+
const matches = text.matchAll(match);
|
94
|
+
for (const m of matches) {
|
95
|
+
if (m.index !== void 0) {
|
96
|
+
const start = from + m.index;
|
97
|
+
const end = start + m[0].length;
|
98
|
+
builder.add(start, end, annotationMark);
|
99
|
+
}
|
100
|
+
}
|
101
|
+
}
|
102
|
+
this.decorations = builder.finish();
|
269
103
|
}
|
270
|
-
|
271
|
-
|
272
|
-
});
|
273
|
-
return [
|
274
|
-
annotationsState,
|
275
|
-
EditorView.decorations.compute([
|
276
|
-
annotationsState
|
277
|
-
], (state) => {
|
278
|
-
const annotations2 = state.field(annotationsState);
|
279
|
-
const decorations = annotations2.map((annotation) => {
|
280
|
-
const range = Cursor.getRangeFromCursor(state, annotation.cursor);
|
281
|
-
return range && annotationMark.range(range.from, range.to);
|
282
|
-
}).filter(isNotFalsy);
|
283
|
-
return Decoration.set(decorations);
|
104
|
+
}, {
|
105
|
+
decorations: (v) => v.decorations
|
284
106
|
}),
|
285
|
-
|
107
|
+
EditorView.theme({
|
108
|
+
".cm-annotation": {
|
109
|
+
textDecoration: "underline",
|
110
|
+
textDecorationStyle: "wavy",
|
111
|
+
textDecorationColor: "var(--dx-errorText)"
|
112
|
+
}
|
113
|
+
})
|
286
114
|
];
|
287
115
|
};
|
288
|
-
var styles = EditorView.theme({
|
289
|
-
".cm-annotation": {
|
290
|
-
textDecoration: "underline",
|
291
|
-
textDecorationStyle: "wavy",
|
292
|
-
textDecorationColor: "var(--dx-error)"
|
293
|
-
}
|
294
|
-
});
|
295
116
|
|
296
117
|
// packages/ui/react-ui-editor/src/extensions/autocomplete.ts
|
297
118
|
import { autocompletion, completionKeymap } from "@codemirror/autocomplete";
|
298
119
|
import { markdownLanguage } from "@codemirror/lang-markdown";
|
299
120
|
import { keymap } from "@codemirror/view";
|
300
|
-
var autocomplete = ({
|
121
|
+
var autocomplete = ({ activateOnTyping, override, onSearch } = {}) => {
|
301
122
|
const extensions = [
|
302
123
|
// https://codemirror.net/docs/ref/#view.keymap
|
303
124
|
// https://discuss.codemirror.net/t/how-can-i-replace-the-default-autocompletion-keymap-v6/3322
|
@@ -306,15 +127,13 @@ var autocomplete = ({ debug, activateOnTyping, override, onSearch } = {}) => {
|
|
306
127
|
// https://codemirror.net/examples/autocompletion
|
307
128
|
// https://codemirror.net/docs/ref/#autocomplete.autocompletion
|
308
129
|
autocompletion({
|
309
|
-
activateOnTyping,
|
310
130
|
override,
|
311
|
-
|
312
|
-
tooltipClass: () => "shadow rounded"
|
131
|
+
activateOnTyping
|
313
132
|
})
|
314
133
|
];
|
315
134
|
if (onSearch) {
|
316
135
|
extensions.push(
|
317
|
-
// TODO(burdon): Optional decoration via addToOptions
|
136
|
+
// TODO(burdon): Optional decoration via addToOptions.
|
318
137
|
markdownLanguage.data.of({
|
319
138
|
autocomplete: (context) => {
|
320
139
|
const match = context.matchBefore(/\w*/);
|
@@ -334,20 +153,20 @@ var autocomplete = ({ debug, activateOnTyping, override, onSearch } = {}) => {
|
|
334
153
|
|
335
154
|
// packages/ui/react-ui-editor/src/extensions/automerge/automerge.ts
|
336
155
|
import { next as A3 } from "@automerge/automerge";
|
337
|
-
import { StateField
|
338
|
-
import { EditorView as EditorView2, ViewPlugin } from "@codemirror/view";
|
156
|
+
import { StateField } from "@codemirror/state";
|
157
|
+
import { EditorView as EditorView2, ViewPlugin as ViewPlugin2 } from "@codemirror/view";
|
339
158
|
|
340
159
|
// packages/ui/react-ui-editor/src/extensions/automerge/cursor.ts
|
341
|
-
import { log
|
160
|
+
import { log } from "@dxos/log";
|
342
161
|
import { fromCursor, toCursor } from "@dxos/react-client/echo";
|
343
|
-
var
|
162
|
+
var __dxlog_file = "/home/runner/work/dxos/dxos/packages/ui/react-ui-editor/src/extensions/automerge/cursor.ts";
|
344
163
|
var cursorConverter = (accessor) => ({
|
345
164
|
toCursor: (pos, assoc) => {
|
346
165
|
try {
|
347
166
|
return toCursor(accessor, pos, assoc);
|
348
167
|
} catch (err) {
|
349
|
-
|
350
|
-
F:
|
168
|
+
log.catch(err, void 0, {
|
169
|
+
F: __dxlog_file,
|
351
170
|
L: 15,
|
352
171
|
S: void 0,
|
353
172
|
C: (f, a) => f(...a)
|
@@ -359,8 +178,8 @@ var cursorConverter = (accessor) => ({
|
|
359
178
|
try {
|
360
179
|
return fromCursor(accessor, cursor);
|
361
180
|
} catch (err) {
|
362
|
-
|
363
|
-
F:
|
181
|
+
log.catch(err, void 0, {
|
182
|
+
F: __dxlog_file,
|
364
183
|
L: 24,
|
365
184
|
S: void 0,
|
366
185
|
C: (f, a) => f(...a)
|
@@ -532,12 +351,12 @@ var Syncer = class {
|
|
532
351
|
this._state = _state;
|
533
352
|
this._pending = false;
|
534
353
|
}
|
535
|
-
reconcile(view,
|
354
|
+
reconcile(view, editor2) {
|
536
355
|
if (this._pending) {
|
537
356
|
return;
|
538
357
|
}
|
539
358
|
this._pending = true;
|
540
|
-
if (
|
359
|
+
if (editor2) {
|
541
360
|
this.onEditorChange(view);
|
542
361
|
} else {
|
543
362
|
this.onAutomergeChange(view);
|
@@ -568,70 +387,230 @@ var Syncer = class {
|
|
568
387
|
}
|
569
388
|
};
|
570
389
|
|
571
|
-
// packages/ui/react-ui-editor/src/
|
572
|
-
|
573
|
-
|
574
|
-
|
575
|
-
|
576
|
-
|
577
|
-
|
578
|
-
|
579
|
-
|
580
|
-
|
581
|
-
|
582
|
-
|
583
|
-
|
584
|
-
|
585
|
-
|
586
|
-
|
587
|
-
|
588
|
-
|
589
|
-
|
590
|
-
|
591
|
-
|
592
|
-
|
593
|
-
|
594
|
-
|
595
|
-
|
596
|
-
|
597
|
-
|
598
|
-
|
599
|
-
|
600
|
-
|
601
|
-
|
602
|
-
|
603
|
-
|
604
|
-
|
605
|
-
|
606
|
-
|
607
|
-
|
608
|
-
|
609
|
-
|
610
|
-
|
611
|
-
|
612
|
-
|
613
|
-
|
614
|
-
|
615
|
-
|
616
|
-
|
617
|
-
|
618
|
-
|
619
|
-
|
620
|
-
|
621
|
-
|
622
|
-
|
623
|
-
|
624
|
-
|
625
|
-
|
626
|
-
|
627
|
-
|
628
|
-
|
629
|
-
|
630
|
-
|
631
|
-
|
632
|
-
|
633
|
-
|
634
|
-
|
390
|
+
// packages/ui/react-ui-editor/src/util/facet.ts
|
391
|
+
import { Facet } from "@codemirror/state";
|
392
|
+
var singleValueFacet = (defaultValue) => Facet.define({
|
393
|
+
// Called immediately.
|
394
|
+
combine: (providers) => {
|
395
|
+
return providers[0] ?? defaultValue;
|
396
|
+
}
|
397
|
+
});
|
398
|
+
|
399
|
+
// packages/ui/react-ui-editor/src/util/cursor.ts
|
400
|
+
var overlap = (a, b) => a.from <= b.to && a.to >= b.from;
|
401
|
+
var defaultCursorConverter = {
|
402
|
+
toCursor: (position) => position.toString(),
|
403
|
+
fromCursor: (cursor) => parseInt(cursor)
|
404
|
+
};
|
405
|
+
var Cursor = class _Cursor {
|
406
|
+
static {
|
407
|
+
this.converter = singleValueFacet(defaultCursorConverter);
|
408
|
+
}
|
409
|
+
static {
|
410
|
+
this.getCursorFromRange = (state, range) => {
|
411
|
+
const cursorConverter2 = state.facet(_Cursor.converter);
|
412
|
+
const from = cursorConverter2.toCursor(range.from);
|
413
|
+
const to = cursorConverter2.toCursor(range.to, -1);
|
414
|
+
return [
|
415
|
+
from,
|
416
|
+
to
|
417
|
+
].join(":");
|
418
|
+
};
|
419
|
+
}
|
420
|
+
static {
|
421
|
+
this.getRangeFromCursor = (state, cursor) => {
|
422
|
+
const cursorConverter2 = state.facet(_Cursor.converter);
|
423
|
+
const parts = cursor.split(":");
|
424
|
+
const from = cursorConverter2.fromCursor(parts[0]);
|
425
|
+
const to = cursorConverter2.fromCursor(parts[1]);
|
426
|
+
return from !== void 0 && to !== void 0 ? {
|
427
|
+
from,
|
428
|
+
to
|
429
|
+
} : void 0;
|
430
|
+
};
|
431
|
+
}
|
432
|
+
};
|
433
|
+
|
434
|
+
// packages/ui/react-ui-editor/src/util/debug.ts
|
435
|
+
import { log as log2 } from "@dxos/log";
|
436
|
+
var __dxlog_file2 = "/home/runner/work/dxos/dxos/packages/ui/react-ui-editor/src/util/debug.ts";
|
437
|
+
var wrapWithCatch = (fn) => {
|
438
|
+
return (...args) => {
|
439
|
+
try {
|
440
|
+
return fn(...args);
|
441
|
+
} catch (err) {
|
442
|
+
log2.catch(err, void 0, {
|
443
|
+
F: __dxlog_file2,
|
444
|
+
L: 15,
|
445
|
+
S: void 0,
|
446
|
+
C: (f, a) => f(...a)
|
447
|
+
});
|
448
|
+
}
|
449
|
+
};
|
450
|
+
};
|
451
|
+
var callbackWrapper = (fn) => (...args) => {
|
452
|
+
try {
|
453
|
+
return fn(...args);
|
454
|
+
} catch (err) {
|
455
|
+
log2.catch(err, void 0, {
|
456
|
+
F: __dxlog_file2,
|
457
|
+
L: 29,
|
458
|
+
S: void 0,
|
459
|
+
C: (f, a) => f(...a)
|
460
|
+
});
|
461
|
+
}
|
462
|
+
};
|
463
|
+
var debugDispatcher = (trs, view) => {
|
464
|
+
logChanges(trs);
|
465
|
+
view.update(trs);
|
466
|
+
};
|
467
|
+
var logChanges = (trs) => {
|
468
|
+
const changes = trs.flatMap((tr) => {
|
469
|
+
if (tr.changes.empty) {
|
470
|
+
return void 0;
|
471
|
+
}
|
472
|
+
const changes2 = [];
|
473
|
+
tr.changes.iterChanges((fromA, toA, fromB, toB, inserted) => changes2.push(JSON.stringify({
|
474
|
+
fromA,
|
475
|
+
toA,
|
476
|
+
fromB,
|
477
|
+
toB,
|
478
|
+
inserted: inserted.toString()
|
479
|
+
})));
|
480
|
+
return changes2;
|
481
|
+
}).filter(Boolean);
|
482
|
+
if (changes.length) {
|
483
|
+
log2("changes", {
|
484
|
+
changes
|
485
|
+
}, {
|
486
|
+
F: __dxlog_file2,
|
487
|
+
L: 62,
|
488
|
+
S: void 0,
|
489
|
+
C: (f, a) => f(...a)
|
490
|
+
});
|
491
|
+
}
|
492
|
+
};
|
493
|
+
|
494
|
+
// packages/ui/react-ui-editor/src/util/dom.ts
|
495
|
+
var flattenRect = (rect, left) => {
|
496
|
+
const x = left ? rect.left : rect.right;
|
497
|
+
return {
|
498
|
+
left: x,
|
499
|
+
right: x,
|
500
|
+
top: rect.top,
|
501
|
+
bottom: rect.bottom
|
502
|
+
};
|
503
|
+
};
|
504
|
+
var scratchRange;
|
505
|
+
var textRange = (node, from, to = from) => {
|
506
|
+
const range = scratchRange || (scratchRange = document.createRange());
|
507
|
+
range.setEnd(node, to);
|
508
|
+
range.setStart(node, from);
|
509
|
+
return range;
|
510
|
+
};
|
511
|
+
var clientRectsFor = (dom) => {
|
512
|
+
if (dom.nodeType === 3) {
|
513
|
+
return textRange(dom, 0, dom.nodeValue.length).getClientRects();
|
514
|
+
} else if (dom.nodeType === 1) {
|
515
|
+
return dom.getClientRects();
|
516
|
+
} else {
|
517
|
+
return [];
|
518
|
+
}
|
519
|
+
};
|
520
|
+
|
521
|
+
// packages/ui/react-ui-editor/src/util/react.tsx
|
522
|
+
import React from "react";
|
523
|
+
import { createRoot } from "react-dom/client";
|
524
|
+
import { ThemeProvider, Tooltip } from "@dxos/react-ui";
|
525
|
+
import { defaultTx } from "@dxos/react-ui-theme";
|
526
|
+
var createElement = (tag, options, children) => {
|
527
|
+
const el = document.createElement(tag);
|
528
|
+
if (options?.className) {
|
529
|
+
el.className = options.className;
|
530
|
+
}
|
531
|
+
if (children) {
|
532
|
+
el.append(...Array.isArray(children) ? children : [
|
533
|
+
children
|
534
|
+
]);
|
535
|
+
}
|
536
|
+
return el;
|
537
|
+
};
|
538
|
+
var renderRoot = (root, node) => {
|
539
|
+
createRoot(root).render(/* @__PURE__ */ React.createElement(ThemeProvider, {
|
540
|
+
tx: defaultTx
|
541
|
+
}, node));
|
542
|
+
return root;
|
543
|
+
};
|
544
|
+
var createRenderer = (Component) => (el, props) => {
|
545
|
+
renderRoot(el, /* @__PURE__ */ React.createElement(ThemeProvider, {
|
546
|
+
tx: defaultTx
|
547
|
+
}, /* @__PURE__ */ React.createElement(Tooltip.Provider, null, /* @__PURE__ */ React.createElement(Component, props))));
|
548
|
+
};
|
549
|
+
|
550
|
+
// packages/ui/react-ui-editor/src/extensions/automerge/automerge.ts
|
551
|
+
var automerge = (accessor) => {
|
552
|
+
const syncState = StateField.define({
|
553
|
+
create: () => ({
|
554
|
+
path: accessor.path.slice(),
|
555
|
+
lastHeads: A3.getHeads(accessor.handle.doc()),
|
556
|
+
unreconciledTransactions: []
|
557
|
+
}),
|
558
|
+
update: (value, tr) => {
|
559
|
+
const result = {
|
560
|
+
path: accessor.path.slice(),
|
561
|
+
lastHeads: value.lastHeads,
|
562
|
+
unreconciledTransactions: value.unreconciledTransactions.slice()
|
563
|
+
};
|
564
|
+
let clearUnreconciled = false;
|
565
|
+
for (const effect of tr.effects) {
|
566
|
+
if (effect.is(updateHeadsEffect)) {
|
567
|
+
result.lastHeads = effect.value.newHeads;
|
568
|
+
clearUnreconciled = true;
|
569
|
+
}
|
570
|
+
}
|
571
|
+
if (clearUnreconciled) {
|
572
|
+
result.unreconciledTransactions = [];
|
573
|
+
} else {
|
574
|
+
if (!isReconcile(tr)) {
|
575
|
+
result.unreconciledTransactions.push(tr);
|
576
|
+
}
|
577
|
+
}
|
578
|
+
return result;
|
579
|
+
}
|
580
|
+
});
|
581
|
+
const syncer = new Syncer(accessor.handle, syncState);
|
582
|
+
return [
|
583
|
+
Cursor.converter.of(cursorConverter(accessor)),
|
584
|
+
// Track heads.
|
585
|
+
syncState,
|
586
|
+
// Reconcile external updates.
|
587
|
+
ViewPlugin2.fromClass(class {
|
588
|
+
constructor(_view) {
|
589
|
+
this._view = _view;
|
590
|
+
this._handleChange = () => {
|
591
|
+
syncer.reconcile(this._view, false);
|
592
|
+
};
|
593
|
+
accessor.handle.addListener("change", this._handleChange);
|
594
|
+
}
|
595
|
+
destroy() {
|
596
|
+
accessor.handle.removeListener("change", this._handleChange);
|
597
|
+
}
|
598
|
+
}),
|
599
|
+
// Reconcile local updates.
|
600
|
+
EditorView2.updateListener.of(({ view, changes }) => {
|
601
|
+
if (!changes.empty) {
|
602
|
+
syncer.reconcile(view, true);
|
603
|
+
}
|
604
|
+
})
|
605
|
+
];
|
606
|
+
};
|
607
|
+
|
608
|
+
// packages/ui/react-ui-editor/src/extensions/awareness/awareness.ts
|
609
|
+
import { Annotation as Annotation2, RangeSet } from "@codemirror/state";
|
610
|
+
import { Decoration as Decoration2, EditorView as EditorView3, ViewPlugin as ViewPlugin3, WidgetType } from "@codemirror/view";
|
611
|
+
import { Event } from "@dxos/async";
|
612
|
+
import { Context } from "@dxos/context";
|
613
|
+
var __dxlog_file3 = "/home/runner/work/dxos/dxos/packages/ui/react-ui-editor/src/extensions/awareness/awareness.ts";
|
635
614
|
var dummyProvider = {
|
636
615
|
remoteStateChange: new Event(),
|
637
616
|
open: () => {
|
@@ -647,10 +626,10 @@ var RemoteSelectionChangedAnnotation = Annotation2.define();
|
|
647
626
|
var awareness = (provider = dummyProvider) => {
|
648
627
|
return [
|
649
628
|
awarenessProvider.of(provider),
|
650
|
-
|
629
|
+
ViewPlugin3.fromClass(RemoteSelectionsDecorator, {
|
651
630
|
decorations: (value) => value.decorations
|
652
631
|
}),
|
653
|
-
|
632
|
+
styles
|
654
633
|
];
|
655
634
|
};
|
656
635
|
var RemoteSelectionsDecorator = class {
|
@@ -693,7 +672,7 @@ var RemoteSelectionsDecorator = class {
|
|
693
672
|
} : void 0);
|
694
673
|
}
|
695
674
|
_updateRemoteSelections(view) {
|
696
|
-
const
|
675
|
+
const decorations2 = [];
|
697
676
|
const awarenessStates = this._provider.getRemoteStates();
|
698
677
|
for (const state of awarenessStates) {
|
699
678
|
const anchor = state.position?.anchor ? this._cursorConverter.fromCursor(state.position.anchor) : null;
|
@@ -708,7 +687,7 @@ var RemoteSelectionsDecorator = class {
|
|
708
687
|
const darkColor = state.info.darkColor;
|
709
688
|
const lightColor = state.info.lightColor;
|
710
689
|
if (startLine.number === endLine.number) {
|
711
|
-
|
690
|
+
decorations2.push({
|
712
691
|
from: start,
|
713
692
|
to: end,
|
714
693
|
value: Decoration2.mark({
|
@@ -719,7 +698,7 @@ var RemoteSelectionsDecorator = class {
|
|
719
698
|
})
|
720
699
|
});
|
721
700
|
} else {
|
722
|
-
|
701
|
+
decorations2.push({
|
723
702
|
from: start,
|
724
703
|
to: startLine.from + startLine.length,
|
725
704
|
value: Decoration2.mark({
|
@@ -729,7 +708,7 @@ var RemoteSelectionsDecorator = class {
|
|
729
708
|
class: "cm-collab-selection"
|
730
709
|
})
|
731
710
|
});
|
732
|
-
|
711
|
+
decorations2.push({
|
733
712
|
from: endLine.from,
|
734
713
|
to: end,
|
735
714
|
value: Decoration2.mark({
|
@@ -741,7 +720,7 @@ var RemoteSelectionsDecorator = class {
|
|
741
720
|
});
|
742
721
|
for (let i = startLine.number + 1; i < endLine.number; i++) {
|
743
722
|
const linePos = view.state.doc.line(i).from;
|
744
|
-
|
723
|
+
decorations2.push({
|
745
724
|
from: linePos,
|
746
725
|
to: linePos,
|
747
726
|
value: Decoration2.line({
|
@@ -753,7 +732,7 @@ var RemoteSelectionsDecorator = class {
|
|
753
732
|
});
|
754
733
|
}
|
755
734
|
}
|
756
|
-
|
735
|
+
decorations2.push({
|
757
736
|
from: head,
|
758
737
|
to: head,
|
759
738
|
value: Decoration2.widget({
|
@@ -763,14 +742,12 @@ var RemoteSelectionsDecorator = class {
|
|
763
742
|
})
|
764
743
|
});
|
765
744
|
}
|
766
|
-
this.decorations = Decoration2.set(
|
745
|
+
this.decorations = Decoration2.set(decorations2, true);
|
767
746
|
}
|
768
747
|
};
|
769
748
|
var RemoteCaretWidget = class extends WidgetType {
|
770
749
|
constructor(_name, _color) {
|
771
|
-
super();
|
772
|
-
this._name = _name;
|
773
|
-
this._color = _color;
|
750
|
+
super(), this._name = _name, this._color = _color;
|
774
751
|
}
|
775
752
|
toDOM() {
|
776
753
|
const span = document.createElement("span");
|
@@ -802,7 +779,7 @@ var RemoteCaretWidget = class extends WidgetType {
|
|
802
779
|
return true;
|
803
780
|
}
|
804
781
|
};
|
805
|
-
var
|
782
|
+
var styles = EditorView3.theme({
|
806
783
|
".cm-collab-selection": {},
|
807
784
|
".cm-collab-selectionLine": {
|
808
785
|
padding: 0,
|
@@ -1281,10 +1258,10 @@ var random = (min, max) => {
|
|
1281
1258
|
import { StateEffect as StateEffect2 } from "@codemirror/state";
|
1282
1259
|
|
1283
1260
|
// packages/ui/react-ui-editor/src/extensions/command/state.ts
|
1284
|
-
import { StateField as
|
1261
|
+
import { StateField as StateField2 } from "@codemirror/state";
|
1285
1262
|
import { showTooltip } from "@codemirror/view";
|
1286
1263
|
var commandConfig = singleValueFacet();
|
1287
|
-
var commandState =
|
1264
|
+
var commandState = StateField2.define({
|
1288
1265
|
create: () => ({}),
|
1289
1266
|
update: (state, tr) => {
|
1290
1267
|
for (const effect of tr.effects) {
|
@@ -1393,14 +1370,14 @@ var commandKeyBindings = [
|
|
1393
1370
|
import { EditorView as EditorView6, keymap as keymap3 } from "@codemirror/view";
|
1394
1371
|
|
1395
1372
|
// packages/ui/react-ui-editor/src/extensions/command/hint.ts
|
1396
|
-
import { RangeSetBuilder } from "@codemirror/state";
|
1397
|
-
import { Decoration as Decoration3, EditorView as EditorView5, ViewPlugin as
|
1398
|
-
var hintViewPlugin = ({ onHint }) =>
|
1373
|
+
import { RangeSetBuilder as RangeSetBuilder2 } from "@codemirror/state";
|
1374
|
+
import { Decoration as Decoration3, EditorView as EditorView5, ViewPlugin as ViewPlugin4, WidgetType as WidgetType2 } from "@codemirror/view";
|
1375
|
+
var hintViewPlugin = ({ onHint }) => ViewPlugin4.fromClass(class {
|
1399
1376
|
constructor() {
|
1400
|
-
this.
|
1377
|
+
this.decorations = Decoration3.none;
|
1401
1378
|
}
|
1402
1379
|
update(update2) {
|
1403
|
-
const builder = new
|
1380
|
+
const builder = new RangeSetBuilder2();
|
1404
1381
|
const cState = update2.view.state.field(commandState, false);
|
1405
1382
|
if (!cState?.tooltip) {
|
1406
1383
|
const selection = update2.view.state.selection.main;
|
@@ -1409,22 +1386,21 @@ var hintViewPlugin = ({ onHint }) => ViewPlugin3.fromClass(class {
|
|
1409
1386
|
const hint = onHint();
|
1410
1387
|
if (hint) {
|
1411
1388
|
builder.add(selection.from, selection.to, Decoration3.widget({
|
1412
|
-
widget: new
|
1389
|
+
widget: new Hint(hint)
|
1413
1390
|
}));
|
1414
1391
|
}
|
1415
1392
|
}
|
1416
1393
|
}
|
1417
|
-
this.
|
1394
|
+
this.decorations = builder.finish();
|
1418
1395
|
}
|
1419
1396
|
}, {
|
1420
1397
|
provide: (plugin) => [
|
1421
|
-
EditorView5.decorations.of((view) => view.plugin(plugin)?.
|
1398
|
+
EditorView5.decorations.of((view) => view.plugin(plugin)?.decorations ?? Decoration3.none)
|
1422
1399
|
]
|
1423
1400
|
});
|
1424
|
-
var
|
1401
|
+
var Hint = class extends WidgetType2 {
|
1425
1402
|
constructor(content) {
|
1426
|
-
super();
|
1427
|
-
this.content = content;
|
1403
|
+
super(), this.content = content;
|
1428
1404
|
}
|
1429
1405
|
toDOM() {
|
1430
1406
|
const wrap = document.createElement("span");
|
@@ -1461,79 +1437,12 @@ var CommandHint = class extends WidgetType2 {
|
|
1461
1437
|
}
|
1462
1438
|
};
|
1463
1439
|
|
1464
|
-
// packages/ui/react-ui-editor/src/extensions/command/menu.ts
|
1465
|
-
import { ViewPlugin as ViewPlugin4 } from "@codemirror/view";
|
1466
|
-
var floatingMenu = (options) => ViewPlugin4.fromClass(class {
|
1467
|
-
constructor(view) {
|
1468
|
-
this.rafId = null;
|
1469
|
-
this.view = view;
|
1470
|
-
const container = view.scrollDOM;
|
1471
|
-
if (getComputedStyle(container).position === "static") {
|
1472
|
-
container.style.position = "relative";
|
1473
|
-
}
|
1474
|
-
this.button = document.createElement("div");
|
1475
|
-
this.button.style.position = "absolute";
|
1476
|
-
this.button.style.zIndex = "10";
|
1477
|
-
this.button.style.display = "none";
|
1478
|
-
options.renderMenu(this.button, {
|
1479
|
-
onAction: () => openCommand(view)
|
1480
|
-
}, view);
|
1481
|
-
container.appendChild(this.button);
|
1482
|
-
container.addEventListener("scroll", this.scheduleUpdate.bind(this));
|
1483
|
-
this.scheduleUpdate();
|
1484
|
-
}
|
1485
|
-
update(update2) {
|
1486
|
-
if (update2.transactions.some((tr) => tr.effects.some((effect) => effect.is(openEffect)))) {
|
1487
|
-
this.button.style.display = "none";
|
1488
|
-
} else if (update2.transactions.some((tr) => tr.effects.some((effect) => effect.is(closeEffect)))) {
|
1489
|
-
this.button.style.display = "block";
|
1490
|
-
} else if (update2.selectionSet || update2.viewportChanged || update2.docChanged || update2.geometryChanged) {
|
1491
|
-
this.scheduleUpdate();
|
1492
|
-
}
|
1493
|
-
}
|
1494
|
-
scheduleUpdate() {
|
1495
|
-
if (this.rafId != null) {
|
1496
|
-
cancelAnimationFrame(this.rafId);
|
1497
|
-
}
|
1498
|
-
this.rafId = requestAnimationFrame(this.updateButtonPosition.bind(this));
|
1499
|
-
}
|
1500
|
-
updateButtonPosition() {
|
1501
|
-
const pos = this.view.state.selection.main.head;
|
1502
|
-
const lineBlock = this.view.lineBlockAt(pos);
|
1503
|
-
const domInfo = this.view.domAtPos(lineBlock.from);
|
1504
|
-
let node = domInfo.node;
|
1505
|
-
while (node && !(node instanceof HTMLElement)) {
|
1506
|
-
node = node.parentNode;
|
1507
|
-
}
|
1508
|
-
if (!node) {
|
1509
|
-
this.button.style.display = "none";
|
1510
|
-
return;
|
1511
|
-
}
|
1512
|
-
const lineRect = node.getBoundingClientRect();
|
1513
|
-
const containerRect = this.view.scrollDOM.getBoundingClientRect();
|
1514
|
-
const offsetTop = lineRect.top - containerRect.top + this.view.scrollDOM.scrollTop;
|
1515
|
-
const offsetLeft = this.view.scrollDOM.clientWidth + this.view.scrollDOM.scrollLeft - lineRect.x;
|
1516
|
-
this.button.style.top = `${offsetTop}px`;
|
1517
|
-
this.button.style.left = `${offsetLeft}px`;
|
1518
|
-
this.button.style.display = "block";
|
1519
|
-
}
|
1520
|
-
destroy() {
|
1521
|
-
this.button.remove();
|
1522
|
-
if (this.rafId != null) {
|
1523
|
-
cancelAnimationFrame(this.rafId);
|
1524
|
-
}
|
1525
|
-
}
|
1526
|
-
});
|
1527
|
-
|
1528
1440
|
// packages/ui/react-ui-editor/src/extensions/command/command.ts
|
1529
1441
|
var command = (options = {}) => {
|
1530
1442
|
return [
|
1531
1443
|
keymap3.of(commandKeyBindings),
|
1532
1444
|
commandConfig.of(options),
|
1533
1445
|
commandState,
|
1534
|
-
options.renderMenu ? floatingMenu({
|
1535
|
-
renderMenu: options.renderMenu
|
1536
|
-
}) : [],
|
1537
1446
|
options.onHint ? hintViewPlugin({
|
1538
1447
|
onHint: options.onHint
|
1539
1448
|
}) : [],
|
@@ -1548,28 +1457,174 @@ var command = (options = {}) => {
|
|
1548
1457
|
];
|
1549
1458
|
};
|
1550
1459
|
|
1551
|
-
// packages/ui/react-ui-editor/src/extensions/
|
1552
|
-
import {
|
1553
|
-
|
1554
|
-
|
1555
|
-
|
1556
|
-
|
1557
|
-
|
1558
|
-
|
1559
|
-
|
1560
|
-
|
1561
|
-
|
1562
|
-
|
1563
|
-
|
1564
|
-
|
1565
|
-
|
1566
|
-
|
1567
|
-
|
1568
|
-
|
1569
|
-
|
1570
|
-
|
1571
|
-
|
1572
|
-
|
1460
|
+
// packages/ui/react-ui-editor/src/extensions/command/menu.ts
|
1461
|
+
import { ViewPlugin as ViewPlugin5 } from "@codemirror/view";
|
1462
|
+
var floatingMenu = (options = {}) => [
|
1463
|
+
ViewPlugin5.fromClass(class {
|
1464
|
+
constructor(view) {
|
1465
|
+
this.rafId = null;
|
1466
|
+
this.view = view;
|
1467
|
+
const container = view.scrollDOM;
|
1468
|
+
if (getComputedStyle(container).position === "static") {
|
1469
|
+
container.style.position = "relative";
|
1470
|
+
}
|
1471
|
+
const icon = document.createElement("dx-icon");
|
1472
|
+
icon.setAttribute("icon", options.icon ?? "ph--dots-three-outline--regular");
|
1473
|
+
const button = document.createElement("button");
|
1474
|
+
button.appendChild(icon);
|
1475
|
+
button.classList.add("grid", "items-center", "justify-center", "w-8", "h-8");
|
1476
|
+
this.tag = document.createElement("dx-ref-tag");
|
1477
|
+
this.tag.classList.add("border-none", "fixed", "p-0");
|
1478
|
+
this.tag.appendChild(button);
|
1479
|
+
container.appendChild(this.tag);
|
1480
|
+
container.addEventListener("scroll", this.scheduleUpdate.bind(this));
|
1481
|
+
this.scheduleUpdate();
|
1482
|
+
}
|
1483
|
+
update(update2) {
|
1484
|
+
if (update2.transactions.some((tr) => tr.effects.some((effect) => effect.is(openEffect)))) {
|
1485
|
+
this.tag.style.display = "none";
|
1486
|
+
} else if (update2.transactions.some((tr) => tr.effects.some((effect) => effect.is(closeEffect)))) {
|
1487
|
+
this.tag.style.display = "block";
|
1488
|
+
} else if (update2.selectionSet || update2.viewportChanged || update2.docChanged || update2.geometryChanged) {
|
1489
|
+
this.scheduleUpdate();
|
1490
|
+
}
|
1491
|
+
}
|
1492
|
+
updateButtonPosition() {
|
1493
|
+
const { x, width } = this.view.contentDOM.getBoundingClientRect();
|
1494
|
+
const pos = this.view.state.selection.main.head;
|
1495
|
+
const line = this.view.lineBlockAt(pos);
|
1496
|
+
const coords = this.view.coordsAtPos(line.from);
|
1497
|
+
if (!coords) {
|
1498
|
+
return;
|
1499
|
+
}
|
1500
|
+
const lineHeight = coords.bottom - coords.top;
|
1501
|
+
const dy = (lineHeight - (options.height ?? 32)) / 2;
|
1502
|
+
const offsetTop = coords.top + dy;
|
1503
|
+
const offsetLeft = x + width + (options.padding ?? 8);
|
1504
|
+
this.tag.style.top = `${offsetTop}px`;
|
1505
|
+
this.tag.style.left = `${offsetLeft}px`;
|
1506
|
+
this.tag.style.display = "block";
|
1507
|
+
}
|
1508
|
+
scheduleUpdate() {
|
1509
|
+
if (this.rafId != null) {
|
1510
|
+
cancelAnimationFrame(this.rafId);
|
1511
|
+
}
|
1512
|
+
this.rafId = requestAnimationFrame(this.updateButtonPosition.bind(this));
|
1513
|
+
}
|
1514
|
+
destroy() {
|
1515
|
+
this.tag.remove();
|
1516
|
+
if (this.rafId != null) {
|
1517
|
+
cancelAnimationFrame(this.rafId);
|
1518
|
+
}
|
1519
|
+
}
|
1520
|
+
})
|
1521
|
+
];
|
1522
|
+
|
1523
|
+
// packages/ui/react-ui-editor/src/extensions/command/typeahead.ts
|
1524
|
+
import { EditorSelection, Prec, RangeSetBuilder as RangeSetBuilder3 } from "@codemirror/state";
|
1525
|
+
import { Decoration as Decoration4, keymap as keymap4, ViewPlugin as ViewPlugin6 } from "@codemirror/view";
|
1526
|
+
var typeahead = ({ onComplete } = {}) => {
|
1527
|
+
let hint;
|
1528
|
+
const complete = (view) => {
|
1529
|
+
if (!hint) {
|
1530
|
+
return false;
|
1531
|
+
}
|
1532
|
+
const selection = view.state.selection.main;
|
1533
|
+
view.dispatch({
|
1534
|
+
changes: [
|
1535
|
+
{
|
1536
|
+
from: selection.from,
|
1537
|
+
to: selection.to,
|
1538
|
+
insert: hint
|
1539
|
+
}
|
1540
|
+
],
|
1541
|
+
selection: EditorSelection.cursor(selection.from + hint.length)
|
1542
|
+
});
|
1543
|
+
return true;
|
1544
|
+
};
|
1545
|
+
return [
|
1546
|
+
ViewPlugin6.fromClass(class {
|
1547
|
+
constructor() {
|
1548
|
+
this.decorations = Decoration4.none;
|
1549
|
+
}
|
1550
|
+
update(update2) {
|
1551
|
+
const builder = new RangeSetBuilder3();
|
1552
|
+
const selection = update2.view.state.selection.main;
|
1553
|
+
const line = update2.view.state.doc.lineAt(selection.from);
|
1554
|
+
if (selection.from === selection.to && selection.from === line.to) {
|
1555
|
+
const str = update2.state.sliceDoc(line.from, selection.from);
|
1556
|
+
hint = onComplete?.({
|
1557
|
+
line: str
|
1558
|
+
});
|
1559
|
+
if (hint) {
|
1560
|
+
builder.add(selection.from, selection.to, Decoration4.widget({
|
1561
|
+
widget: new Hint(hint)
|
1562
|
+
}));
|
1563
|
+
}
|
1564
|
+
}
|
1565
|
+
this.decorations = builder.finish();
|
1566
|
+
}
|
1567
|
+
}, {
|
1568
|
+
decorations: (v) => v.decorations
|
1569
|
+
}),
|
1570
|
+
// Keys.
|
1571
|
+
Prec.highest(keymap4.of([
|
1572
|
+
{
|
1573
|
+
key: "Tab",
|
1574
|
+
preventDefault: true,
|
1575
|
+
run: complete
|
1576
|
+
},
|
1577
|
+
{
|
1578
|
+
key: "ArrowRight",
|
1579
|
+
preventDefault: true,
|
1580
|
+
run: complete
|
1581
|
+
}
|
1582
|
+
]))
|
1583
|
+
];
|
1584
|
+
};
|
1585
|
+
var staticCompletion = (completions, defaultCompletion) => ({ line }) => {
|
1586
|
+
if (line.length === 0 && defaultCompletion) {
|
1587
|
+
return defaultCompletion;
|
1588
|
+
}
|
1589
|
+
const words = line.split(/\s+/).filter(Boolean);
|
1590
|
+
if (words.length) {
|
1591
|
+
const word = words.at(-1);
|
1592
|
+
for (const completion of completions) {
|
1593
|
+
const match = matchCompletion(completion, word);
|
1594
|
+
if (match) {
|
1595
|
+
return match;
|
1596
|
+
}
|
1597
|
+
}
|
1598
|
+
}
|
1599
|
+
};
|
1600
|
+
var matchCompletion = (completion, word) => {
|
1601
|
+
if (completion.length > word.length && completion.startsWith(word)) {
|
1602
|
+
return completion.slice(word.length);
|
1603
|
+
}
|
1604
|
+
};
|
1605
|
+
|
1606
|
+
// packages/ui/react-ui-editor/src/extensions/comments.ts
|
1607
|
+
import { invertedEffects } from "@codemirror/commands";
|
1608
|
+
import { StateEffect as StateEffect3, StateField as StateField3 } from "@codemirror/state";
|
1609
|
+
import { hoverTooltip, keymap as keymap6, Decoration as Decoration5, EditorView as EditorView8, ViewPlugin as ViewPlugin7 } from "@codemirror/view";
|
1610
|
+
import sortBy from "lodash.sortby";
|
1611
|
+
import { useEffect } from "react";
|
1612
|
+
import { debounce as debounce2 } from "@dxos/async";
|
1613
|
+
import { log as log4 } from "@dxos/log";
|
1614
|
+
import { isNonNullable } from "@dxos/util";
|
1615
|
+
|
1616
|
+
// packages/ui/react-ui-editor/src/extensions/selection.ts
|
1617
|
+
import { Transaction } from "@codemirror/state";
|
1618
|
+
import { EditorView as EditorView7, keymap as keymap5 } from "@codemirror/view";
|
1619
|
+
import { debounce } from "@dxos/async";
|
1620
|
+
import { invariant as invariant3 } from "@dxos/invariant";
|
1621
|
+
import { isNotFalsy } from "@dxos/util";
|
1622
|
+
var __dxlog_file6 = "/home/runner/work/dxos/dxos/packages/ui/react-ui-editor/src/extensions/selection.ts";
|
1623
|
+
var documentId = singleValueFacet();
|
1624
|
+
var stateRestoreAnnotation = "dxos.org/cm/state-restore";
|
1625
|
+
var createEditorStateTransaction = ({ scrollTo, selection }) => {
|
1626
|
+
return {
|
1627
|
+
selection,
|
1573
1628
|
scrollIntoView: !scrollTo,
|
1574
1629
|
effects: scrollTo ? EditorView7.scrollIntoView(scrollTo, {
|
1575
1630
|
yMargin: 96
|
@@ -1636,7 +1691,7 @@ var selectionState = ({ getState, setState } = {}) => {
|
|
1636
1691
|
}
|
1637
1692
|
}
|
1638
1693
|
}),
|
1639
|
-
getState &&
|
1694
|
+
getState && keymap5.of([
|
1640
1695
|
{
|
1641
1696
|
key: "ctrl-r",
|
1642
1697
|
run: (view) => {
|
@@ -1648,7 +1703,7 @@ var selectionState = ({ getState, setState } = {}) => {
|
|
1648
1703
|
}
|
1649
1704
|
}
|
1650
1705
|
])
|
1651
|
-
].filter(
|
1706
|
+
].filter(isNotFalsy);
|
1652
1707
|
};
|
1653
1708
|
|
1654
1709
|
// packages/ui/react-ui-editor/src/extensions/comments.ts
|
@@ -1656,7 +1711,7 @@ var __dxlog_file7 = "/home/runner/work/dxos/dxos/packages/ui/react-ui-editor/src
|
|
1656
1711
|
var setComments = StateEffect3.define();
|
1657
1712
|
var setSelection = StateEffect3.define();
|
1658
1713
|
var setCommentState = StateEffect3.define();
|
1659
|
-
var commentsState =
|
1714
|
+
var commentsState = StateField3.define({
|
1660
1715
|
create: (state) => ({
|
1661
1716
|
id: state.facet(documentId),
|
1662
1717
|
comments: [],
|
@@ -1694,7 +1749,7 @@ var commentsState = StateField4.define({
|
|
1694
1749
|
return value;
|
1695
1750
|
}
|
1696
1751
|
});
|
1697
|
-
var
|
1752
|
+
var styles2 = EditorView8.theme({
|
1698
1753
|
".cm-comment, .cm-comment-current": {
|
1699
1754
|
margin: "0 -3px",
|
1700
1755
|
padding: "3px",
|
@@ -1707,7 +1762,7 @@ var styles3 = EditorView8.theme({
|
|
1707
1762
|
textDecoration: "underline"
|
1708
1763
|
}
|
1709
1764
|
});
|
1710
|
-
var createCommentMark = (id, isCurrent) =>
|
1765
|
+
var createCommentMark = (id, isCurrent) => Decoration5.mark({
|
1711
1766
|
class: isCurrent ? "cm-comment-current" : "cm-comment",
|
1712
1767
|
attributes: {
|
1713
1768
|
"data-testid": "cm-comment",
|
@@ -1718,12 +1773,12 @@ var commentsDecorations = EditorView8.decorations.compute([
|
|
1718
1773
|
commentsState
|
1719
1774
|
], (state) => {
|
1720
1775
|
const { selection: { current }, comments: comments2 } = state.field(commentsState);
|
1721
|
-
const
|
1776
|
+
const decorations2 = sortBy(comments2 ?? [], (range) => range.range.from)?.flatMap((comment) => {
|
1722
1777
|
const range = comment.range;
|
1723
1778
|
if (!range) {
|
1724
1779
|
log4.warn("Invalid range:", range, {
|
1725
1780
|
F: __dxlog_file7,
|
1726
|
-
L:
|
1781
|
+
L: 135,
|
1727
1782
|
S: void 0,
|
1728
1783
|
C: (f, a) => f(...a)
|
1729
1784
|
});
|
@@ -1734,7 +1789,7 @@ var commentsDecorations = EditorView8.decorations.compute([
|
|
1734
1789
|
const mark = createCommentMark(comment.comment.id, comment.comment.id === current);
|
1735
1790
|
return mark.range(range.from, range.to);
|
1736
1791
|
}).filter(isNonNullable);
|
1737
|
-
return
|
1792
|
+
return Decoration5.set(decorations2);
|
1738
1793
|
});
|
1739
1794
|
var commentClickedEffect = StateEffect3.define();
|
1740
1795
|
var handleCommentClick = EditorView8.domEventHandlers({
|
@@ -1895,11 +1950,11 @@ var comments = (options = {}) => {
|
|
1895
1950
|
commentsState,
|
1896
1951
|
commentsDecorations,
|
1897
1952
|
handleCommentClick,
|
1898
|
-
|
1953
|
+
styles2,
|
1899
1954
|
//
|
1900
1955
|
// Keymap.
|
1901
1956
|
//
|
1902
|
-
options.onCreate &&
|
1957
|
+
options.onCreate && keymap6.of([
|
1903
1958
|
{
|
1904
1959
|
key: shortcut,
|
1905
1960
|
run: callbackWrapper(createComment)
|
@@ -2037,22 +2092,6 @@ var scrollThreadIntoView = (view, id, center = true) => {
|
|
2037
2092
|
}
|
2038
2093
|
}
|
2039
2094
|
};
|
2040
|
-
var selectionOverlapsComment = (state) => {
|
2041
|
-
const commentState = state.field(commentsState, false);
|
2042
|
-
if (commentState === void 0) {
|
2043
|
-
return false;
|
2044
|
-
}
|
2045
|
-
const { selection } = state;
|
2046
|
-
for (const range of selection.ranges) {
|
2047
|
-
if (commentState.comments.some(({ range: commentRange }) => overlap(commentRange, range))) {
|
2048
|
-
return true;
|
2049
|
-
}
|
2050
|
-
}
|
2051
|
-
return false;
|
2052
|
-
};
|
2053
|
-
var hasActiveSelection = (state) => {
|
2054
|
-
return state.selection.ranges.some((range) => !range.empty);
|
2055
|
-
};
|
2056
2095
|
var ExternalCommentSync = class {
|
2057
2096
|
constructor(view, id, subscribe, getComments) {
|
2058
2097
|
this.destroy = () => {
|
@@ -2072,21 +2111,11 @@ var ExternalCommentSync = class {
|
|
2072
2111
|
this.unsubscribe = subscribe(updateComments);
|
2073
2112
|
}
|
2074
2113
|
};
|
2075
|
-
var createExternalCommentSync = (id, subscribe, getComments) =>
|
2114
|
+
var createExternalCommentSync = (id, subscribe, getComments) => ViewPlugin7.fromClass(class {
|
2076
2115
|
constructor(view) {
|
2077
2116
|
return new ExternalCommentSync(view, id, subscribe, getComments);
|
2078
2117
|
}
|
2079
2118
|
});
|
2080
|
-
var useCommentState = (state) => {
|
2081
|
-
return useMemo2(() => EditorView8.updateListener.of((update2) => {
|
2082
|
-
if (update2.docChanged || update2.selectionSet) {
|
2083
|
-
state.comment = selectionOverlapsComment(update2.state);
|
2084
|
-
state.selection = hasActiveSelection(update2.state);
|
2085
|
-
}
|
2086
|
-
}), [
|
2087
|
-
state
|
2088
|
-
]);
|
2089
|
-
};
|
2090
2119
|
var useComments = (view, id, comments2) => {
|
2091
2120
|
useEffect(() => {
|
2092
2121
|
if (view) {
|
@@ -2101,28 +2130,15 @@ var useComments = (view, id, comments2) => {
|
|
2101
2130
|
}
|
2102
2131
|
});
|
2103
2132
|
};
|
2104
|
-
var useCommentClickListener = (onCommentClick) => {
|
2105
|
-
return useMemo2(() => EditorView8.updateListener.of((update2) => {
|
2106
|
-
update2.transactions.forEach((transaction) => {
|
2107
|
-
transaction.effects.forEach((effect) => {
|
2108
|
-
if (effect.is(commentClickedEffect)) {
|
2109
|
-
onCommentClick(effect.value);
|
2110
|
-
}
|
2111
|
-
});
|
2112
|
-
});
|
2113
|
-
}), [
|
2114
|
-
onCommentClick
|
2115
|
-
]);
|
2116
|
-
};
|
2117
2133
|
|
2118
2134
|
// packages/ui/react-ui-editor/src/extensions/debug.ts
|
2119
2135
|
import { syntaxTree } from "@codemirror/language";
|
2120
|
-
import { StateField as
|
2136
|
+
import { StateField as StateField4 } from "@codemirror/state";
|
2121
2137
|
var debugNodeLogger = (log9 = console.log) => {
|
2122
2138
|
const logTokens = (state) => syntaxTree(state).iterate({
|
2123
2139
|
enter: (node) => log9(node.type)
|
2124
2140
|
});
|
2125
|
-
return
|
2141
|
+
return StateField4.define({
|
2126
2142
|
create: (state) => logTokens(state),
|
2127
2143
|
update: (_, tr) => logTokens(tr.state)
|
2128
2144
|
});
|
@@ -2130,7 +2146,7 @@ var debugNodeLogger = (log9 = console.log) => {
|
|
2130
2146
|
|
2131
2147
|
// packages/ui/react-ui-editor/src/extensions/dnd.ts
|
2132
2148
|
import { dropCursor, EditorView as EditorView9 } from "@codemirror/view";
|
2133
|
-
var
|
2149
|
+
var styles3 = EditorView9.theme({
|
2134
2150
|
".cm-dropCursor": {
|
2135
2151
|
borderLeft: "2px solid var(--dx-accentText)",
|
2136
2152
|
color: "var(--dx-accentText)",
|
@@ -2142,7 +2158,7 @@ var styles4 = EditorView9.theme({
|
|
2142
2158
|
});
|
2143
2159
|
var dropFile = (options = {}) => {
|
2144
2160
|
return [
|
2145
|
-
|
2161
|
+
styles3,
|
2146
2162
|
dropCursor(),
|
2147
2163
|
EditorView9.domEventHandlers({
|
2148
2164
|
drop: (event, view) => {
|
@@ -2171,18 +2187,18 @@ import { bracketMatching, defaultHighlightStyle, syntaxHighlighting } from "@cod
|
|
2171
2187
|
import { searchKeymap } from "@codemirror/search";
|
2172
2188
|
import { EditorState } from "@codemirror/state";
|
2173
2189
|
import { oneDarkHighlightStyle } from "@codemirror/theme-one-dark";
|
2174
|
-
import { EditorView as EditorView11, drawSelection, dropCursor as dropCursor2, highlightActiveLine, keymap as
|
2190
|
+
import { EditorView as EditorView11, ViewPlugin as ViewPlugin8, drawSelection, dropCursor as dropCursor2, highlightActiveLine, keymap as keymap7, lineNumbers, placeholder, scrollPastEnd } from "@codemirror/view";
|
2175
2191
|
import defaultsDeep2 from "lodash.defaultsdeep";
|
2176
2192
|
import merge from "lodash.merge";
|
2177
2193
|
import { generateName } from "@dxos/display-name";
|
2178
2194
|
import { log as log5 } from "@dxos/log";
|
2179
|
-
import { hexToHue, isNotFalsy as
|
2195
|
+
import { hexToHue, isNotFalsy as isNotFalsy2 } from "@dxos/util";
|
2180
2196
|
|
2181
2197
|
// packages/ui/react-ui-editor/src/extensions/focus.ts
|
2182
|
-
import { StateEffect as StateEffect4, StateField as
|
2198
|
+
import { StateEffect as StateEffect4, StateField as StateField5 } from "@codemirror/state";
|
2183
2199
|
import { EditorView as EditorView10 } from "@codemirror/view";
|
2184
2200
|
var focusEffect = StateEffect4.define();
|
2185
|
-
var focusField =
|
2201
|
+
var focusField = StateField5.define({
|
2186
2202
|
create: () => false,
|
2187
2203
|
update: (value, tr) => {
|
2188
2204
|
for (const effect of tr.effects) {
|
@@ -2229,8 +2245,8 @@ var theme = {
|
|
2229
2245
|
};
|
2230
2246
|
|
2231
2247
|
// packages/ui/react-ui-editor/src/styles/tokens.ts
|
2232
|
-
import get from "lodash.get";
|
2233
2248
|
import { tokens } from "@dxos/react-ui-theme";
|
2249
|
+
import { get } from "@dxos/util";
|
2234
2250
|
var getToken = (path, defaultValue) => {
|
2235
2251
|
const value = get(tokens, path, defaultValue);
|
2236
2252
|
return value?.toString() ?? "";
|
@@ -2353,19 +2369,25 @@ var defaultTheme = {
|
|
2353
2369
|
*/
|
2354
2370
|
".cm-tooltip.cm-tooltip-autocomplete": {
|
2355
2371
|
marginTop: "4px",
|
2356
|
-
marginLeft: "-3px"
|
2372
|
+
marginLeft: "-3px",
|
2373
|
+
borderColor: "var(--dx-separator)",
|
2374
|
+
borderTop: "none"
|
2357
2375
|
},
|
2358
2376
|
".cm-tooltip.cm-tooltip-autocomplete > ul": {
|
2359
2377
|
maxHeight: "20em"
|
2360
2378
|
},
|
2361
|
-
".cm-tooltip.cm-tooltip-autocomplete > ul > li": {
|
2362
|
-
|
2379
|
+
".cm-tooltip.cm-tooltip-autocomplete > ul > li": {
|
2380
|
+
padding: "4px"
|
2381
|
+
},
|
2382
|
+
".cm-tooltip.cm-tooltip-autocomplete > ul > li[aria-selected]": {
|
2383
|
+
background: "var(--dx-hoverSurface)"
|
2384
|
+
},
|
2363
2385
|
".cm-tooltip.cm-tooltip-autocomplete > ul > completion-section": {
|
2364
2386
|
paddingLeft: "4px !important",
|
2365
2387
|
borderBottom: "none !important",
|
2366
2388
|
color: "var(--dx-accentText)"
|
2367
2389
|
},
|
2368
|
-
".cm-
|
2390
|
+
".cm-completionInfo": {
|
2369
2391
|
width: "360px !important",
|
2370
2392
|
margin: "-10px 1px 0 1px",
|
2371
2393
|
padding: "8px !important",
|
@@ -2415,7 +2437,7 @@ var defaultTheme = {
|
|
2415
2437
|
backgroundColor: "var(--dx-input)"
|
2416
2438
|
},
|
2417
2439
|
".cm-panel input:focus, .cm-panel button:focus": {
|
2418
|
-
outline: "1px solid var(--dx-
|
2440
|
+
outline: "1px solid var(--dx-neutralFocusIndicator)"
|
2419
2441
|
},
|
2420
2442
|
".cm-panel label": {
|
2421
2443
|
display: "inline-flex",
|
@@ -2428,7 +2450,7 @@ var defaultTheme = {
|
|
2428
2450
|
height: "8px",
|
2429
2451
|
marginRight: "6px !important",
|
2430
2452
|
padding: "2px !important",
|
2431
|
-
color: "var(--dx-
|
2453
|
+
color: "var(--dx-neutralFocusIndicator)"
|
2432
2454
|
},
|
2433
2455
|
".cm-panel button": {
|
2434
2456
|
"&:hover": {
|
@@ -2471,7 +2493,7 @@ var createBasicExtensions = (_props) => {
|
|
2471
2493
|
EditorView11.exceptionSink.of((err) => {
|
2472
2494
|
log5.catch(err, void 0, {
|
2473
2495
|
F: __dxlog_file8,
|
2474
|
-
L:
|
2496
|
+
L: 98,
|
2475
2497
|
S: void 0,
|
2476
2498
|
C: (f, a) => f(...a)
|
2477
2499
|
});
|
@@ -2494,7 +2516,7 @@ var createBasicExtensions = (_props) => {
|
|
2494
2516
|
props.scrollPastEnd && scrollPastEnd(),
|
2495
2517
|
props.tabSize && EditorState.tabSize.of(props.tabSize),
|
2496
2518
|
// https://codemirror.net/docs/ref/#view.KeyBinding
|
2497
|
-
|
2519
|
+
keymap7.of([
|
2498
2520
|
...(props.keymap && keymaps[props.keymap]) ?? [],
|
2499
2521
|
// NOTE: Tabs are also configured by markdown extension.
|
2500
2522
|
// https://codemirror.net/docs/ref/#commands.indentWithTab
|
@@ -2514,19 +2536,19 @@ var createBasicExtensions = (_props) => {
|
|
2514
2536
|
preventDefault: true,
|
2515
2537
|
run: () => true
|
2516
2538
|
}
|
2517
|
-
].filter(
|
2518
|
-
].filter(
|
2539
|
+
].filter(isNotFalsy2))
|
2540
|
+
].filter(isNotFalsy2);
|
2519
2541
|
};
|
2520
2542
|
var defaultThemeSlots = {
|
2521
2543
|
editor: {
|
2522
2544
|
className: "w-full bs-full"
|
2523
2545
|
}
|
2524
2546
|
};
|
2525
|
-
var createThemeExtensions = ({ themeMode, styles:
|
2547
|
+
var createThemeExtensions = ({ themeMode, styles: styles4, syntaxHighlighting: _syntaxHighlighting, slots: _slots } = {}) => {
|
2526
2548
|
const slots = defaultsDeep2({}, _slots, defaultThemeSlots);
|
2527
2549
|
return [
|
2528
2550
|
EditorView11.darkTheme.of(themeMode === "dark"),
|
2529
|
-
EditorView11.baseTheme(
|
2551
|
+
EditorView11.baseTheme(styles4 ? merge({}, defaultTheme, styles4) : defaultTheme),
|
2530
2552
|
// https://github.com/codemirror/theme-one-dark
|
2531
2553
|
_syntaxHighlighting && (themeMode === "dark" ? syntaxHighlighting(oneDarkHighlightStyle) : syntaxHighlighting(defaultHighlightStyle)),
|
2532
2554
|
slots.editor?.className && EditorView11.editorAttributes.of({
|
@@ -2534,8 +2556,13 @@ var createThemeExtensions = ({ themeMode, styles: styles5, syntaxHighlighting: _
|
|
2534
2556
|
}),
|
2535
2557
|
slots.content?.className && EditorView11.contentAttributes.of({
|
2536
2558
|
class: slots.content.className
|
2559
|
+
}),
|
2560
|
+
slots.scroll?.className && ViewPlugin8.fromClass(class {
|
2561
|
+
constructor(view) {
|
2562
|
+
view.scrollDOM.classList.add(slots.scroll.className);
|
2563
|
+
}
|
2537
2564
|
})
|
2538
|
-
].filter(
|
2565
|
+
].filter(isNotFalsy2);
|
2539
2566
|
};
|
2540
2567
|
var createDataExtensions = ({ id, text, space, identity }) => {
|
2541
2568
|
const extensions = [];
|
@@ -2597,6 +2624,50 @@ var folding = (_props = {}) => [
|
|
2597
2624
|
})
|
2598
2625
|
];
|
2599
2626
|
|
2627
|
+
// packages/ui/react-ui-editor/src/extensions/json.ts
|
2628
|
+
import { json, jsonParseLinter } from "@codemirror/lang-json";
|
2629
|
+
import { linter } from "@codemirror/lint";
|
2630
|
+
import Ajv from "ajv";
|
2631
|
+
var createJsonExtensions = ({ schema } = {}) => {
|
2632
|
+
let lintSource = jsonParseLinter();
|
2633
|
+
if (schema) {
|
2634
|
+
const ajv = new Ajv({
|
2635
|
+
allErrors: false
|
2636
|
+
});
|
2637
|
+
const validate = ajv.compile(schema);
|
2638
|
+
lintSource = schemaLinter(validate);
|
2639
|
+
}
|
2640
|
+
return [
|
2641
|
+
json(),
|
2642
|
+
linter(lintSource)
|
2643
|
+
];
|
2644
|
+
};
|
2645
|
+
var schemaLinter = (validate) => (view) => {
|
2646
|
+
try {
|
2647
|
+
const jsonText = view.state.doc.toString();
|
2648
|
+
const jsonData = JSON.parse(jsonText);
|
2649
|
+
const valid = validate(jsonData);
|
2650
|
+
if (valid) {
|
2651
|
+
return [];
|
2652
|
+
}
|
2653
|
+
return validate.errors?.map((err) => ({
|
2654
|
+
from: 0,
|
2655
|
+
to: jsonText.length,
|
2656
|
+
severity: "error",
|
2657
|
+
message: `${err.instancePath || "(root)"} ${err.message}`
|
2658
|
+
})) ?? [];
|
2659
|
+
} catch (err) {
|
2660
|
+
return [
|
2661
|
+
{
|
2662
|
+
from: 0,
|
2663
|
+
to: view.state.doc.length,
|
2664
|
+
severity: "error",
|
2665
|
+
message: "Invalid JSON: " + err.message
|
2666
|
+
}
|
2667
|
+
];
|
2668
|
+
}
|
2669
|
+
};
|
2670
|
+
|
2600
2671
|
// packages/ui/react-ui-editor/src/extensions/listener.ts
|
2601
2672
|
import { EditorView as EditorView13 } from "@codemirror/view";
|
2602
2673
|
var listener = ({ onFocus, onChange }) => {
|
@@ -2614,23 +2685,23 @@ var listener = ({ onFocus, onChange }) => {
|
|
2614
2685
|
// packages/ui/react-ui-editor/src/extensions/markdown/formatting.ts
|
2615
2686
|
import { snippet } from "@codemirror/autocomplete";
|
2616
2687
|
import { syntaxTree as syntaxTree2 } from "@codemirror/language";
|
2617
|
-
import { EditorSelection } from "@codemirror/state";
|
2618
|
-
import { EditorView as EditorView14, keymap as
|
2619
|
-
import { useMemo as
|
2688
|
+
import { EditorSelection as EditorSelection2 } from "@codemirror/state";
|
2689
|
+
import { EditorView as EditorView14, keymap as keymap8 } from "@codemirror/view";
|
2690
|
+
import { useMemo as useMemo2 } from "react";
|
2620
2691
|
var formattingEquals = (a, b) => a.blockType === b.blockType && a.strong === b.strong && a.emphasis === b.emphasis && a.strikethrough === b.strikethrough && a.code === b.code && a.link === b.link && a.listStyle === b.listStyle && a.blockQuote === b.blockQuote;
|
2621
|
-
var Inline
|
2622
|
-
(function(Inline2) {
|
2692
|
+
var Inline = /* @__PURE__ */ function(Inline2) {
|
2623
2693
|
Inline2[Inline2["Strong"] = 0] = "Strong";
|
2624
2694
|
Inline2[Inline2["Emphasis"] = 1] = "Emphasis";
|
2625
2695
|
Inline2[Inline2["Strikethrough"] = 2] = "Strikethrough";
|
2626
2696
|
Inline2[Inline2["Code"] = 3] = "Code";
|
2627
|
-
|
2628
|
-
|
2629
|
-
|
2697
|
+
return Inline2;
|
2698
|
+
}({});
|
2699
|
+
var List = /* @__PURE__ */ function(List2) {
|
2630
2700
|
List2[List2["Ordered"] = 0] = "Ordered";
|
2631
2701
|
List2[List2["Bullet"] = 1] = "Bullet";
|
2632
2702
|
List2[List2["Task"] = 2] = "Task";
|
2633
|
-
|
2703
|
+
return List2;
|
2704
|
+
}({});
|
2634
2705
|
var setHeading = (level) => {
|
2635
2706
|
return ({ state, dispatch }) => {
|
2636
2707
|
const { selection: { ranges }, doc } = state;
|
@@ -2735,7 +2806,7 @@ var setStyle = (type, enable) => {
|
|
2735
2806
|
to: range.head + found + marker.length
|
2736
2807
|
}
|
2737
2808
|
],
|
2738
|
-
range:
|
2809
|
+
range: EditorSelection2.cursor(range.from - marker.length)
|
2739
2810
|
};
|
2740
2811
|
}
|
2741
2812
|
}
|
@@ -2863,13 +2934,13 @@ var setStyle = (type, enable) => {
|
|
2863
2934
|
from: range.head,
|
2864
2935
|
insert: marker + marker
|
2865
2936
|
},
|
2866
|
-
range:
|
2937
|
+
range: EditorSelection2.cursor(range.head + marker.length)
|
2867
2938
|
};
|
2868
2939
|
}
|
2869
2940
|
const changeSet = state.changes(changes2.concat(changesAtEnd));
|
2870
2941
|
return {
|
2871
2942
|
changes: changeSet,
|
2872
|
-
range: range.empty && !changeSet.empty ?
|
2943
|
+
range: range.empty && !changeSet.empty ? EditorSelection2.cursor(range.head + marker.length) : EditorSelection2.range(changeSet.mapPos(range.from, 1), changeSet.mapPos(range.to, -1))
|
2873
2944
|
};
|
2874
2945
|
});
|
2875
2946
|
dispatch(state.update(changes, {
|
@@ -3069,7 +3140,7 @@ var addLink = ({ url, image: image2 } = {}) => {
|
|
3069
3140
|
const changeSet = state.changes(changes2.concat(changesAfter));
|
3070
3141
|
return {
|
3071
3142
|
changes: changeSet,
|
3072
|
-
range:
|
3143
|
+
range: EditorSelection2.cursor(changeSet.mapPos(to, 1) - cursorOffset - (url ? url.length + 2 : 0))
|
3073
3144
|
};
|
3074
3145
|
});
|
3075
3146
|
if (changes.changes.empty) {
|
@@ -3503,7 +3574,7 @@ var toggleCodeblock = (target) => {
|
|
3503
3574
|
};
|
3504
3575
|
var formattingKeymap = (_options = {}) => {
|
3505
3576
|
return [
|
3506
|
-
|
3577
|
+
keymap8.of([
|
3507
3578
|
{
|
3508
3579
|
key: "meta-b",
|
3509
3580
|
run: toggleStrong
|
@@ -3704,7 +3775,7 @@ var getFormatting = (state) => {
|
|
3704
3775
|
};
|
3705
3776
|
};
|
3706
3777
|
var useFormattingState = (state) => {
|
3707
|
-
return
|
3778
|
+
return useMemo2(() => EditorView14.updateListener.of((update2) => {
|
3708
3779
|
if (update2.docChanged || update2.selectionSet) {
|
3709
3780
|
Object.entries(getFormatting(update2.state)).forEach(([key, active]) => {
|
3710
3781
|
state[key] = active;
|
@@ -3713,7 +3784,7 @@ var useFormattingState = (state) => {
|
|
3713
3784
|
}), []);
|
3714
3785
|
};
|
3715
3786
|
|
3716
|
-
// packages/ui/react-ui-editor/src/extensions/markdown/
|
3787
|
+
// packages/ui/react-ui-editor/src/extensions/markdown/action.ts
|
3717
3788
|
var processEditorPayload = (view, { type, data }) => {
|
3718
3789
|
let inlineType, listType;
|
3719
3790
|
switch (type) {
|
@@ -3769,7 +3840,8 @@ import { markdownLanguage as markdownLanguage3, markdown } from "@codemirror/lan
|
|
3769
3840
|
import { syntaxHighlighting as syntaxHighlighting2 } from "@codemirror/language";
|
3770
3841
|
import { languages } from "@codemirror/language-data";
|
3771
3842
|
import { lintKeymap } from "@codemirror/lint";
|
3772
|
-
import { keymap as
|
3843
|
+
import { keymap as keymap9 } from "@codemirror/view";
|
3844
|
+
import { isNotFalsy as isNotFalsy3 } from "@dxos/util";
|
3773
3845
|
|
3774
3846
|
// packages/ui/react-ui-editor/src/extensions/markdown/highlight.ts
|
3775
3847
|
import { markdownLanguage as markdownLanguage2 } from "@codemirror/lang-markdown";
|
@@ -3951,7 +4023,7 @@ var markdownHighlightStyle = (_options = {}) => {
|
|
3951
4023
|
};
|
3952
4024
|
|
3953
4025
|
// packages/ui/react-ui-editor/src/extensions/markdown/bundle.ts
|
3954
|
-
var createMarkdownExtensions = (
|
4026
|
+
var createMarkdownExtensions = (options = {}) => {
|
3955
4027
|
return [
|
3956
4028
|
// Main extension.
|
3957
4029
|
// https://github.com/codemirror/lang-markdown
|
@@ -3975,21 +4047,21 @@ var createMarkdownExtensions = ({ themeMode } = {}) => {
|
|
3975
4047
|
}),
|
3976
4048
|
// Custom styles.
|
3977
4049
|
syntaxHighlighting2(markdownHighlightStyle()),
|
3978
|
-
|
4050
|
+
keymap9.of([
|
3979
4051
|
// https://codemirror.net/docs/ref/#commands.indentWithTab
|
3980
|
-
indentWithTab2,
|
4052
|
+
options.indentWithTab !== false && indentWithTab2,
|
3981
4053
|
// https://codemirror.net/docs/ref/#commands.defaultKeymap
|
3982
4054
|
...defaultKeymap2,
|
3983
4055
|
...completionKeymap2,
|
3984
4056
|
...lintKeymap
|
3985
|
-
])
|
4057
|
+
].filter(isNotFalsy3))
|
3986
4058
|
];
|
3987
4059
|
};
|
3988
4060
|
|
3989
4061
|
// packages/ui/react-ui-editor/src/extensions/markdown/debug.ts
|
3990
4062
|
import { syntaxTree as syntaxTree3 } from "@codemirror/language";
|
3991
|
-
import { StateField as
|
3992
|
-
var debugTree = (cb) =>
|
4063
|
+
import { StateField as StateField6 } from "@codemirror/state";
|
4064
|
+
var debugTree = (cb) => StateField6.define({
|
3993
4065
|
create: (state) => cb(convertTreeToJson(state)),
|
3994
4066
|
update: (value, tr) => cb(convertTreeToJson(tr.state))
|
3995
4067
|
});
|
@@ -4015,17 +4087,17 @@ var convertTreeToJson = (state) => {
|
|
4015
4087
|
|
4016
4088
|
// packages/ui/react-ui-editor/src/extensions/markdown/decorate.ts
|
4017
4089
|
import { syntaxTree as syntaxTree7 } from "@codemirror/language";
|
4018
|
-
import { RangeSetBuilder as
|
4019
|
-
import { EditorView as EditorView18, Decoration as
|
4090
|
+
import { RangeSetBuilder as RangeSetBuilder5, StateEffect as StateEffect5 } from "@codemirror/state";
|
4091
|
+
import { EditorView as EditorView18, Decoration as Decoration8, WidgetType as WidgetType5, ViewPlugin as ViewPlugin10 } from "@codemirror/view";
|
4020
4092
|
import { invariant as invariant4 } from "@dxos/invariant";
|
4021
4093
|
import { mx as mx2 } from "@dxos/react-ui-theme";
|
4022
4094
|
|
4023
4095
|
// packages/ui/react-ui-editor/src/extensions/markdown/changes.ts
|
4024
4096
|
import { syntaxTree as syntaxTree4 } from "@codemirror/language";
|
4025
4097
|
import { Transaction as Transaction2 } from "@codemirror/state";
|
4026
|
-
import { ViewPlugin as
|
4098
|
+
import { ViewPlugin as ViewPlugin9 } from "@codemirror/view";
|
4027
4099
|
var adjustChanges = () => {
|
4028
|
-
return
|
4100
|
+
return ViewPlugin9.fromClass(class {
|
4029
4101
|
update(update2) {
|
4030
4102
|
const tree = syntaxTree4(update2.state);
|
4031
4103
|
const adjustments = [];
|
@@ -4166,13 +4238,13 @@ var getValidUrl = (str) => {
|
|
4166
4238
|
|
4167
4239
|
// packages/ui/react-ui-editor/src/extensions/markdown/image.ts
|
4168
4240
|
import { syntaxTree as syntaxTree5 } from "@codemirror/language";
|
4169
|
-
import { StateField as
|
4170
|
-
import { Decoration as
|
4241
|
+
import { StateField as StateField7 } from "@codemirror/state";
|
4242
|
+
import { Decoration as Decoration6, EditorView as EditorView15, WidgetType as WidgetType3 } from "@codemirror/view";
|
4171
4243
|
var image = (_options = {}) => {
|
4172
4244
|
return [
|
4173
|
-
|
4245
|
+
StateField7.define({
|
4174
4246
|
create: (state) => {
|
4175
|
-
return
|
4247
|
+
return Decoration6.set(buildDecorations(0, state.doc.length, state));
|
4176
4248
|
},
|
4177
4249
|
update: (value, tr) => {
|
4178
4250
|
if (!tr.docChanged && !tr.selection) {
|
@@ -4200,7 +4272,7 @@ var image = (_options = {}) => {
|
|
4200
4272
|
];
|
4201
4273
|
};
|
4202
4274
|
var buildDecorations = (from, to, state) => {
|
4203
|
-
const
|
4275
|
+
const decorations2 = [];
|
4204
4276
|
const cursor = state.selection.main.head;
|
4205
4277
|
syntaxTree5(state).iterate({
|
4206
4278
|
enter: (node) => {
|
@@ -4213,7 +4285,7 @@ var buildDecorations = (from, to, state) => {
|
|
4213
4285
|
return;
|
4214
4286
|
}
|
4215
4287
|
preloadImage(url);
|
4216
|
-
|
4288
|
+
decorations2.push(Decoration6.replace({
|
4217
4289
|
block: true,
|
4218
4290
|
widget: new ImageWidget(url)
|
4219
4291
|
}).range(hide2 ? node.from : node.to, node.to));
|
@@ -4223,7 +4295,7 @@ var buildDecorations = (from, to, state) => {
|
|
4223
4295
|
from,
|
4224
4296
|
to
|
4225
4297
|
});
|
4226
|
-
return
|
4298
|
+
return decorations2;
|
4227
4299
|
};
|
4228
4300
|
var preloaded = /* @__PURE__ */ new Set();
|
4229
4301
|
var preloadImage = (url) => {
|
@@ -4235,8 +4307,7 @@ var preloadImage = (url) => {
|
|
4235
4307
|
};
|
4236
4308
|
var ImageWidget = class extends WidgetType3 {
|
4237
4309
|
constructor(_url) {
|
4238
|
-
super();
|
4239
|
-
this._url = _url;
|
4310
|
+
super(), this._url = _url;
|
4240
4311
|
}
|
4241
4312
|
eq(other) {
|
4242
4313
|
return this._url === other._url;
|
@@ -4317,8 +4388,9 @@ var formattingStyles = EditorView16.theme({
|
|
4317
4388
|
* Task list.
|
4318
4389
|
*/
|
4319
4390
|
"& .cm-task": {
|
4320
|
-
display: "inline-
|
4321
|
-
width: `${bulletListIndentationWidth}px
|
4391
|
+
display: "inline-flex",
|
4392
|
+
width: `${bulletListIndentationWidth}px`,
|
4393
|
+
height: "20px"
|
4322
4394
|
},
|
4323
4395
|
"& .cm-task-checkbox": {
|
4324
4396
|
display: "grid",
|
@@ -4378,17 +4450,17 @@ var formattingStyles = EditorView16.theme({
|
|
4378
4450
|
|
4379
4451
|
// packages/ui/react-ui-editor/src/extensions/markdown/table.ts
|
4380
4452
|
import { syntaxTree as syntaxTree6 } from "@codemirror/language";
|
4381
|
-
import { RangeSetBuilder as
|
4382
|
-
import { Decoration as
|
4453
|
+
import { RangeSetBuilder as RangeSetBuilder4, StateField as StateField8 } from "@codemirror/state";
|
4454
|
+
import { Decoration as Decoration7, EditorView as EditorView17, WidgetType as WidgetType4 } from "@codemirror/view";
|
4383
4455
|
var table = (options = {}) => {
|
4384
|
-
return
|
4456
|
+
return StateField8.define({
|
4385
4457
|
create: (state) => update(state, options),
|
4386
4458
|
update: (_, tr) => update(tr.state, options),
|
4387
4459
|
provide: (field) => EditorView17.decorations.from(field)
|
4388
4460
|
});
|
4389
4461
|
};
|
4390
4462
|
var update = (state, _options) => {
|
4391
|
-
const builder = new
|
4463
|
+
const builder = new RangeSetBuilder4();
|
4392
4464
|
const cursor = state.selection.main.head;
|
4393
4465
|
const tables = [];
|
4394
4466
|
const getTable = () => tables[tables.length - 1];
|
@@ -4429,12 +4501,12 @@ var update = (state, _options) => {
|
|
4429
4501
|
tables.forEach((table2) => {
|
4430
4502
|
const replace = state.readOnly || cursor < table2.from || cursor > table2.to;
|
4431
4503
|
if (replace) {
|
4432
|
-
builder.add(table2.from, table2.to,
|
4504
|
+
builder.add(table2.from, table2.to, Decoration7.replace({
|
4433
4505
|
block: true,
|
4434
4506
|
widget: new TableWidget(table2)
|
4435
4507
|
}));
|
4436
4508
|
} else {
|
4437
|
-
builder.add(table2.from, table2.to,
|
4509
|
+
builder.add(table2.from, table2.to, Decoration7.mark({
|
4438
4510
|
class: "cm-table"
|
4439
4511
|
}));
|
4440
4512
|
}
|
@@ -4443,8 +4515,7 @@ var update = (state, _options) => {
|
|
4443
4515
|
};
|
4444
4516
|
var TableWidget = class extends WidgetType4 {
|
4445
4517
|
constructor(_table) {
|
4446
|
-
super();
|
4447
|
-
this._table = _table;
|
4518
|
+
super(), this._table = _table;
|
4448
4519
|
}
|
4449
4520
|
eq(other) {
|
4450
4521
|
return this._table.header?.join() === other._table.header?.join() && this._table.rows?.join() === other._table.rows?.join();
|
@@ -4492,9 +4563,7 @@ var HorizontalRuleWidget = class extends WidgetType5 {
|
|
4492
4563
|
};
|
4493
4564
|
var LinkButton = class extends WidgetType5 {
|
4494
4565
|
constructor(url, render) {
|
4495
|
-
super();
|
4496
|
-
this.url = url;
|
4497
|
-
this.render = render;
|
4566
|
+
super(), this.url = url, this.render = render;
|
4498
4567
|
}
|
4499
4568
|
eq(other) {
|
4500
4569
|
return this.url === other.url;
|
@@ -4510,8 +4579,7 @@ var LinkButton = class extends WidgetType5 {
|
|
4510
4579
|
};
|
4511
4580
|
var CheckboxWidget = class extends WidgetType5 {
|
4512
4581
|
constructor(_checked) {
|
4513
|
-
super();
|
4514
|
-
this._checked = _checked;
|
4582
|
+
super(), this._checked = _checked;
|
4515
4583
|
}
|
4516
4584
|
eq(other) {
|
4517
4585
|
return this._checked === other._checked;
|
@@ -4555,9 +4623,7 @@ var CheckboxWidget = class extends WidgetType5 {
|
|
4555
4623
|
};
|
4556
4624
|
var TextWidget = class extends WidgetType5 {
|
4557
4625
|
constructor(text, className) {
|
4558
|
-
super();
|
4559
|
-
this.text = text;
|
4560
|
-
this.className = className;
|
4626
|
+
super(), this.text = text, this.className = className;
|
4561
4627
|
}
|
4562
4628
|
toDOM() {
|
4563
4629
|
const el = document.createElement("span");
|
@@ -4568,29 +4634,29 @@ var TextWidget = class extends WidgetType5 {
|
|
4568
4634
|
return el;
|
4569
4635
|
}
|
4570
4636
|
};
|
4571
|
-
var hide =
|
4572
|
-
var blockQuote =
|
4637
|
+
var hide = Decoration8.replace({});
|
4638
|
+
var blockQuote = Decoration8.line({
|
4573
4639
|
class: "cm-blockquote"
|
4574
4640
|
});
|
4575
|
-
var fencedCodeLine =
|
4641
|
+
var fencedCodeLine = Decoration8.line({
|
4576
4642
|
class: "cm-code cm-codeblock-line"
|
4577
4643
|
});
|
4578
|
-
var fencedCodeLineFirst =
|
4644
|
+
var fencedCodeLineFirst = Decoration8.line({
|
4579
4645
|
class: mx2("cm-code cm-codeblock-line", "cm-codeblock-start")
|
4580
4646
|
});
|
4581
|
-
var fencedCodeLineLast =
|
4647
|
+
var fencedCodeLineLast = Decoration8.line({
|
4582
4648
|
class: mx2("cm-code cm-codeblock-line", "cm-codeblock-end")
|
4583
4649
|
});
|
4584
4650
|
var commentBlockLine = fencedCodeLine;
|
4585
4651
|
var commentBlockLineFirst = fencedCodeLineFirst;
|
4586
4652
|
var commentBlockLineLast = fencedCodeLineLast;
|
4587
|
-
var horizontalRule =
|
4653
|
+
var horizontalRule = Decoration8.replace({
|
4588
4654
|
widget: new HorizontalRuleWidget()
|
4589
4655
|
});
|
4590
|
-
var checkedTask =
|
4656
|
+
var checkedTask = Decoration8.replace({
|
4591
4657
|
widget: new CheckboxWidget(true)
|
4592
4658
|
});
|
4593
|
-
var uncheckedTask =
|
4659
|
+
var uncheckedTask = Decoration8.replace({
|
4594
4660
|
widget: new CheckboxWidget(false)
|
4595
4661
|
});
|
4596
4662
|
var editingRange = (state, range, focus2) => {
|
@@ -4606,8 +4672,8 @@ var autoHideTags = /* @__PURE__ */ new Set([
|
|
4606
4672
|
"SuperscriptMark"
|
4607
4673
|
]);
|
4608
4674
|
var buildDecorations2 = (view, options, focus2) => {
|
4609
|
-
const deco = new
|
4610
|
-
const atomicDeco = new
|
4675
|
+
const deco = new RangeSetBuilder5();
|
4676
|
+
const atomicDeco = new RangeSetBuilder5();
|
4611
4677
|
const { state } = view;
|
4612
4678
|
const headerLevels = [];
|
4613
4679
|
const getHeaderLevels = (node, level) => {
|
@@ -4694,7 +4760,7 @@ var buildDecorations2 = (view, options, focus2) => {
|
|
4694
4760
|
} else {
|
4695
4761
|
const num = headers.slice(from - 1).map((level2) => level2?.number ?? 0).join(".") + " ";
|
4696
4762
|
if (num.length) {
|
4697
|
-
atomicDeco.add(mark.from, mark.from + len,
|
4763
|
+
atomicDeco.add(mark.from, mark.from + len, Decoration8.replace({
|
4698
4764
|
widget: new TextWidget(num, theme.heading(level))
|
4699
4765
|
}));
|
4700
4766
|
}
|
@@ -4719,7 +4785,7 @@ var buildDecorations2 = (view, options, focus2) => {
|
|
4719
4785
|
if (node.from === line.to - 1) {
|
4720
4786
|
return false;
|
4721
4787
|
}
|
4722
|
-
deco.add(line.from, line.from,
|
4788
|
+
deco.add(line.from, line.from, Decoration8.line({
|
4723
4789
|
class: "cm-list-item",
|
4724
4790
|
attributes: {
|
4725
4791
|
style: `padding-left: ${offset}px; text-indent: -${width}px;`
|
@@ -4736,7 +4802,7 @@ var buildDecorations2 = (view, options, focus2) => {
|
|
4736
4802
|
const label = list.type === "OrderedList" ? `${++list.number}.` : Unicode.bulletSmall;
|
4737
4803
|
const line = state.doc.lineAt(node.from);
|
4738
4804
|
const to = state.doc.sliceString(node.to, node.to + 1) === " " ? node.to + 1 : node.to;
|
4739
|
-
atomicDeco.add(line.from, to,
|
4805
|
+
atomicDeco.add(line.from, to, Decoration8.replace({
|
4740
4806
|
widget: new TextWidget(label, list.type === "OrderedList" ? "cm-list-mark cm-list-mark-ordered" : "cm-list-mark cm-list-mark-bullet")
|
4741
4807
|
}));
|
4742
4808
|
break;
|
@@ -4823,7 +4889,7 @@ var buildDecorations2 = (view, options, focus2) => {
|
|
4823
4889
|
if (!editing) {
|
4824
4890
|
atomicDeco.add(node.from, marks[0].to, hide);
|
4825
4891
|
}
|
4826
|
-
deco.add(marks[0].to, marks[1].from,
|
4892
|
+
deco.add(marks[0].to, marks[1].from, Decoration8.mark({
|
4827
4893
|
tagName: "a",
|
4828
4894
|
attributes: {
|
4829
4895
|
class: "cm-link",
|
@@ -4833,7 +4899,7 @@ var buildDecorations2 = (view, options, focus2) => {
|
|
4833
4899
|
}
|
4834
4900
|
}));
|
4835
4901
|
if (!editing) {
|
4836
|
-
atomicDeco.add(marks[1].from, node.to, options.renderLinkButton ?
|
4902
|
+
atomicDeco.add(marks[1].from, node.to, options.renderLinkButton ? Decoration8.replace({
|
4837
4903
|
widget: new LinkButton(url, options.renderLinkButton)
|
4838
4904
|
}) : hide);
|
4839
4905
|
}
|
@@ -4891,7 +4957,7 @@ var buildDecorations2 = (view, options, focus2) => {
|
|
4891
4957
|
var forceUpdate = StateEffect5.define();
|
4892
4958
|
var decorateMarkdown = (options = {}) => {
|
4893
4959
|
return [
|
4894
|
-
|
4960
|
+
ViewPlugin10.fromClass(class {
|
4895
4961
|
constructor(view) {
|
4896
4962
|
({ deco: this.deco, atomicDeco: this.atomicDeco } = buildDecorations2(view, options, view.hasFocus));
|
4897
4963
|
}
|
@@ -4923,9 +4989,9 @@ var decorateMarkdown = (options = {}) => {
|
|
4923
4989
|
}
|
4924
4990
|
}, {
|
4925
4991
|
provide: (plugin) => [
|
4926
|
-
EditorView18.atomicRanges.of((view) => view.plugin(plugin)?.atomicDeco ??
|
4927
|
-
EditorView18.decorations.of((view) => view.plugin(plugin)?.atomicDeco ??
|
4928
|
-
EditorView18.decorations.of((view) => view.plugin(plugin)?.deco ??
|
4992
|
+
EditorView18.atomicRanges.of((view) => view.plugin(plugin)?.atomicDeco ?? Decoration8.none),
|
4993
|
+
EditorView18.decorations.of((view) => view.plugin(plugin)?.atomicDeco ?? Decoration8.none),
|
4994
|
+
EditorView18.decorations.of((view) => view.plugin(plugin)?.deco ?? Decoration8.none)
|
4929
4995
|
]
|
4930
4996
|
}),
|
4931
4997
|
image(),
|
@@ -4970,65 +5036,748 @@ var linkTooltip = (renderTooltip) => {
|
|
4970
5036
|
}
|
4971
5037
|
};
|
4972
5038
|
}
|
4973
|
-
};
|
4974
|
-
}, {
|
4975
|
-
// NOTE: 0 = default of 300ms.
|
4976
|
-
hoverTime: 1
|
5039
|
+
};
|
5040
|
+
}, {
|
5041
|
+
// NOTE: 0 = default of 300ms.
|
5042
|
+
hoverTime: 1
|
5043
|
+
});
|
5044
|
+
};
|
5045
|
+
|
5046
|
+
// packages/ui/react-ui-editor/src/extensions/mention.ts
|
5047
|
+
import { autocompletion as autocompletion2 } from "@codemirror/autocomplete";
|
5048
|
+
import { log as log6 } from "@dxos/log";
|
5049
|
+
var __dxlog_file10 = "/home/runner/work/dxos/dxos/packages/ui/react-ui-editor/src/extensions/mention.ts";
|
5050
|
+
var mention = ({ debug, onSearch }) => {
|
5051
|
+
return autocompletion2({
|
5052
|
+
// TODO(burdon): Not working.
|
5053
|
+
activateOnTyping: true,
|
5054
|
+
// activateOnTypingDelay: 100,
|
5055
|
+
// selectOnOpen: true,
|
5056
|
+
closeOnBlur: !debug,
|
5057
|
+
// defaultKeymap: false,
|
5058
|
+
icons: false,
|
5059
|
+
override: [
|
5060
|
+
(context) => {
|
5061
|
+
log6.info("completion context", {
|
5062
|
+
context
|
5063
|
+
}, {
|
5064
|
+
F: __dxlog_file10,
|
5065
|
+
L: 27,
|
5066
|
+
S: void 0,
|
5067
|
+
C: (f, a) => f(...a)
|
5068
|
+
});
|
5069
|
+
const match = context.matchBefore(/@(\w+)?/);
|
5070
|
+
if (!match || match.from === match.to && !context.explicit) {
|
5071
|
+
return null;
|
5072
|
+
}
|
5073
|
+
return {
|
5074
|
+
from: match.from,
|
5075
|
+
options: onSearch(match.text.slice(1).toLowerCase()).map((value) => ({
|
5076
|
+
label: `@${value}`
|
5077
|
+
}))
|
5078
|
+
};
|
5079
|
+
}
|
5080
|
+
]
|
5081
|
+
});
|
5082
|
+
};
|
5083
|
+
|
5084
|
+
// packages/ui/react-ui-editor/src/extensions/modes.ts
|
5085
|
+
import { keymap as keymap10 } from "@codemirror/view";
|
5086
|
+
import { vim } from "@replit/codemirror-vim";
|
5087
|
+
import { vscodeKeymap } from "@replit/codemirror-vscode-keymap";
|
5088
|
+
import { Schema } from "effect";
|
5089
|
+
var EditorViewModes = [
|
5090
|
+
"preview",
|
5091
|
+
"readonly",
|
5092
|
+
"source"
|
5093
|
+
];
|
5094
|
+
var EditorViewMode = Schema.Union(...EditorViewModes.map((mode) => Schema.Literal(mode)));
|
5095
|
+
var EditorInputModes = [
|
5096
|
+
"default",
|
5097
|
+
"vim",
|
5098
|
+
"vscode"
|
5099
|
+
];
|
5100
|
+
var EditorInputMode = Schema.Union(...EditorInputModes.map((mode) => Schema.Literal(mode)));
|
5101
|
+
var editorInputMode = singleValueFacet({});
|
5102
|
+
var InputModeExtensions = {
|
5103
|
+
default: [],
|
5104
|
+
vscode: [
|
5105
|
+
// https://github.com/replit/codemirror-vscode-keymap
|
5106
|
+
editorInputMode.of({
|
5107
|
+
type: "vscode"
|
5108
|
+
}),
|
5109
|
+
keymap10.of(vscodeKeymap)
|
5110
|
+
],
|
5111
|
+
vim: [
|
5112
|
+
// https://github.com/replit/codemirror-vim
|
5113
|
+
vim(),
|
5114
|
+
editorInputMode.of({
|
5115
|
+
type: "vim",
|
5116
|
+
noTabster: true
|
5117
|
+
}),
|
5118
|
+
keymap10.of([
|
5119
|
+
{
|
5120
|
+
key: "Alt-Escape",
|
5121
|
+
run: (view) => {
|
5122
|
+
view.dom.parentElement?.focus();
|
5123
|
+
return true;
|
5124
|
+
}
|
5125
|
+
}
|
5126
|
+
])
|
5127
|
+
]
|
5128
|
+
};
|
5129
|
+
|
5130
|
+
// packages/ui/react-ui-editor/src/extensions/outliner/outliner.ts
|
5131
|
+
import { Prec as Prec2 } from "@codemirror/state";
|
5132
|
+
import { Decoration as Decoration9, EditorView as EditorView19, ViewPlugin as ViewPlugin12 } from "@codemirror/view";
|
5133
|
+
import { mx as mx3 } from "@dxos/react-ui-theme";
|
5134
|
+
|
5135
|
+
// packages/ui/react-ui-editor/src/extensions/outliner/commands.ts
|
5136
|
+
import { indentMore } from "@codemirror/commands";
|
5137
|
+
import { getIndentUnit } from "@codemirror/language";
|
5138
|
+
import { EditorSelection as EditorSelection3 } from "@codemirror/state";
|
5139
|
+
import { keymap as keymap11 } from "@codemirror/view";
|
5140
|
+
|
5141
|
+
// packages/ui/react-ui-editor/src/extensions/outliner/selection.ts
|
5142
|
+
import { Compartment, Facet as Facet3 } from "@codemirror/state";
|
5143
|
+
|
5144
|
+
// packages/ui/react-ui-editor/src/extensions/outliner/tree.ts
|
5145
|
+
import { syntaxTree as syntaxTree9 } from "@codemirror/language";
|
5146
|
+
import { StateField as StateField9 } from "@codemirror/state";
|
5147
|
+
import { Facet as Facet2 } from "@codemirror/state";
|
5148
|
+
import { invariant as invariant5 } from "@dxos/invariant";
|
5149
|
+
var __dxlog_file11 = "/home/runner/work/dxos/dxos/packages/ui/react-ui-editor/src/extensions/outliner/tree.ts";
|
5150
|
+
var itemToJSON = ({ type, index, level, lineRange, contentRange, children }) => {
|
5151
|
+
return {
|
5152
|
+
type,
|
5153
|
+
index,
|
5154
|
+
level,
|
5155
|
+
lineRange,
|
5156
|
+
contentRange,
|
5157
|
+
children: children.map(itemToJSON)
|
5158
|
+
};
|
5159
|
+
};
|
5160
|
+
var Tree = class {
|
5161
|
+
constructor(node) {
|
5162
|
+
this.type = "root";
|
5163
|
+
this.index = -1;
|
5164
|
+
this.level = -1;
|
5165
|
+
this.children = [];
|
5166
|
+
this.node = node;
|
5167
|
+
this.lineRange = {
|
5168
|
+
from: node.from,
|
5169
|
+
to: node.to
|
5170
|
+
};
|
5171
|
+
this.contentRange = this.lineRange;
|
5172
|
+
}
|
5173
|
+
toJSON() {
|
5174
|
+
return itemToJSON(this);
|
5175
|
+
}
|
5176
|
+
get root() {
|
5177
|
+
return this;
|
5178
|
+
}
|
5179
|
+
traverse(itemOrCb, maybeCb) {
|
5180
|
+
if (typeof itemOrCb === "function") {
|
5181
|
+
return traverse(this, itemOrCb);
|
5182
|
+
} else {
|
5183
|
+
return traverse(itemOrCb, maybeCb);
|
5184
|
+
}
|
5185
|
+
}
|
5186
|
+
/**
|
5187
|
+
* Return the closest item.
|
5188
|
+
*/
|
5189
|
+
find(pos) {
|
5190
|
+
return this.traverse((item) => item.lineRange.from <= pos && item.lineRange.to >= pos ? item : void 0);
|
5191
|
+
}
|
5192
|
+
/**
|
5193
|
+
* Return the first child, next sibling, or parent's next sibling.
|
5194
|
+
*/
|
5195
|
+
next(item, enter = true) {
|
5196
|
+
if (enter && item.children.length > 0) {
|
5197
|
+
return item.children[0];
|
5198
|
+
}
|
5199
|
+
if (item.nextSibling) {
|
5200
|
+
return item.nextSibling;
|
5201
|
+
}
|
5202
|
+
if (item.parent) {
|
5203
|
+
return this.next(item.parent, false);
|
5204
|
+
}
|
5205
|
+
return void 0;
|
5206
|
+
}
|
5207
|
+
/**
|
5208
|
+
* Return the previous sibling, or parent.
|
5209
|
+
*/
|
5210
|
+
prev(item) {
|
5211
|
+
if (item.prevSibling) {
|
5212
|
+
return this.lastDescendant(item.prevSibling);
|
5213
|
+
}
|
5214
|
+
return item.parent?.type === "root" ? void 0 : item.parent;
|
5215
|
+
}
|
5216
|
+
/**
|
5217
|
+
* Return the last descendant of the item, or the item itself if it has no children.
|
5218
|
+
*/
|
5219
|
+
lastDescendant(item) {
|
5220
|
+
return item.children.length > 0 ? this.lastDescendant(item.children.at(-1)) : item;
|
5221
|
+
}
|
5222
|
+
};
|
5223
|
+
var getRange = (tree, item) => {
|
5224
|
+
const lastDescendant = tree.lastDescendant(item);
|
5225
|
+
return [
|
5226
|
+
item.lineRange.from,
|
5227
|
+
lastDescendant.lineRange.to
|
5228
|
+
];
|
5229
|
+
};
|
5230
|
+
var traverse = (root, cb) => {
|
5231
|
+
const t = (item, level) => {
|
5232
|
+
if (item.type !== "root") {
|
5233
|
+
const value = cb(item, level);
|
5234
|
+
if (value != null) {
|
5235
|
+
return value;
|
5236
|
+
}
|
5237
|
+
}
|
5238
|
+
for (const child of item.children) {
|
5239
|
+
const value = t(child, level + 1);
|
5240
|
+
if (value != null) {
|
5241
|
+
return value;
|
5242
|
+
}
|
5243
|
+
}
|
5244
|
+
};
|
5245
|
+
return t(root, root.type === "root" ? -1 : 0);
|
5246
|
+
};
|
5247
|
+
var getListItemContent = (state, item) => {
|
5248
|
+
return state.doc.sliceString(item.contentRange.from, item.contentRange.to);
|
5249
|
+
};
|
5250
|
+
var listItemToString = (item, level = 0) => {
|
5251
|
+
const indent = " ".repeat(level);
|
5252
|
+
const data = {
|
5253
|
+
i: item.index,
|
5254
|
+
n: item.nextSibling?.index ?? "\u2205",
|
5255
|
+
p: item.prevSibling?.index ?? "\u2205",
|
5256
|
+
level: item.level,
|
5257
|
+
node: format([
|
5258
|
+
item.node.from,
|
5259
|
+
item.node.to
|
5260
|
+
]),
|
5261
|
+
line: format([
|
5262
|
+
item.lineRange.from,
|
5263
|
+
item.lineRange.to
|
5264
|
+
]),
|
5265
|
+
content: format([
|
5266
|
+
item.contentRange.from,
|
5267
|
+
item.contentRange.to
|
5268
|
+
])
|
5269
|
+
};
|
5270
|
+
return `${indent}${item.type[0].toUpperCase()}(${Object.entries(data).map(([k, v]) => `${k}=${v}`).join(", ")})`;
|
5271
|
+
};
|
5272
|
+
var format = (value) => JSON.stringify(value, (key, value2) => {
|
5273
|
+
if (typeof value2 === "number") {
|
5274
|
+
return value2.toString().padStart(3, " ");
|
5275
|
+
}
|
5276
|
+
return value2;
|
5277
|
+
}).replaceAll('"', "");
|
5278
|
+
var treeFacet = Facet2.define({
|
5279
|
+
combine: (values) => values[0]
|
5280
|
+
});
|
5281
|
+
var outlinerTree = (options = {}) => {
|
5282
|
+
const buildTree = (state) => {
|
5283
|
+
let tree;
|
5284
|
+
let parent;
|
5285
|
+
let current;
|
5286
|
+
let prev;
|
5287
|
+
let level = -1;
|
5288
|
+
let index = -1;
|
5289
|
+
const prevSiblings = [];
|
5290
|
+
syntaxTree9(state).iterate({
|
5291
|
+
enter: (node) => {
|
5292
|
+
switch (node.name) {
|
5293
|
+
case "Document": {
|
5294
|
+
tree = new Tree(node.node);
|
5295
|
+
current = tree;
|
5296
|
+
break;
|
5297
|
+
}
|
5298
|
+
case "BulletList": {
|
5299
|
+
invariant5(current, void 0, {
|
5300
|
+
F: __dxlog_file11,
|
5301
|
+
L: 217,
|
5302
|
+
S: void 0,
|
5303
|
+
A: [
|
5304
|
+
"current",
|
5305
|
+
""
|
5306
|
+
]
|
5307
|
+
});
|
5308
|
+
parent = current;
|
5309
|
+
if (current) {
|
5310
|
+
current.lineRange.to = current.node.from;
|
5311
|
+
}
|
5312
|
+
prevSiblings[++level] = void 0;
|
5313
|
+
break;
|
5314
|
+
}
|
5315
|
+
case "ListItem": {
|
5316
|
+
invariant5(parent, void 0, {
|
5317
|
+
F: __dxlog_file11,
|
5318
|
+
L: 226,
|
5319
|
+
S: void 0,
|
5320
|
+
A: [
|
5321
|
+
"parent",
|
5322
|
+
""
|
5323
|
+
]
|
5324
|
+
});
|
5325
|
+
const nextSibling = node.node.nextSibling ?? node.node.parent?.nextSibling;
|
5326
|
+
const docRange = {
|
5327
|
+
from: state.doc.lineAt(node.from).from,
|
5328
|
+
to: nextSibling ? nextSibling.from - 1 : state.doc.length
|
5329
|
+
};
|
5330
|
+
current = {
|
5331
|
+
type: "unknown",
|
5332
|
+
index: ++index,
|
5333
|
+
level,
|
5334
|
+
node: node.node,
|
5335
|
+
lineRange: docRange,
|
5336
|
+
contentRange: {
|
5337
|
+
...docRange
|
5338
|
+
},
|
5339
|
+
parent,
|
5340
|
+
prevSibling: prevSiblings[level],
|
5341
|
+
children: []
|
5342
|
+
};
|
5343
|
+
if (current.prevSibling) {
|
5344
|
+
current.prevSibling.nextSibling = current;
|
5345
|
+
}
|
5346
|
+
prevSiblings[level] = current;
|
5347
|
+
if (prev) {
|
5348
|
+
prev.lineRange.to = prev.contentRange.to = current.lineRange.from - 1;
|
5349
|
+
}
|
5350
|
+
prev = current;
|
5351
|
+
parent.children.push(current);
|
5352
|
+
if (parent.lineRange.to === parent.node.from) {
|
5353
|
+
parent.lineRange.to = parent.contentRange.to = current.lineRange.from - 1;
|
5354
|
+
}
|
5355
|
+
break;
|
5356
|
+
}
|
5357
|
+
case "ListMark": {
|
5358
|
+
invariant5(current, void 0, {
|
5359
|
+
F: __dxlog_file11,
|
5360
|
+
L: 270,
|
5361
|
+
S: void 0,
|
5362
|
+
A: [
|
5363
|
+
"current",
|
5364
|
+
""
|
5365
|
+
]
|
5366
|
+
});
|
5367
|
+
current.type = "bullet";
|
5368
|
+
current.contentRange.from = node.from + "- ".length;
|
5369
|
+
break;
|
5370
|
+
}
|
5371
|
+
case "Task": {
|
5372
|
+
invariant5(current, void 0, {
|
5373
|
+
F: __dxlog_file11,
|
5374
|
+
L: 276,
|
5375
|
+
S: void 0,
|
5376
|
+
A: [
|
5377
|
+
"current",
|
5378
|
+
""
|
5379
|
+
]
|
5380
|
+
});
|
5381
|
+
current.type = "task";
|
5382
|
+
break;
|
5383
|
+
}
|
5384
|
+
case "TaskMarker": {
|
5385
|
+
invariant5(current, void 0, {
|
5386
|
+
F: __dxlog_file11,
|
5387
|
+
L: 281,
|
5388
|
+
S: void 0,
|
5389
|
+
A: [
|
5390
|
+
"current",
|
5391
|
+
""
|
5392
|
+
]
|
5393
|
+
});
|
5394
|
+
current.contentRange.from = node.from + "[ ] ".length;
|
5395
|
+
break;
|
5396
|
+
}
|
5397
|
+
}
|
5398
|
+
},
|
5399
|
+
leave: (node) => {
|
5400
|
+
if (node.name === "BulletList") {
|
5401
|
+
invariant5(parent, void 0, {
|
5402
|
+
F: __dxlog_file11,
|
5403
|
+
L: 289,
|
5404
|
+
S: void 0,
|
5405
|
+
A: [
|
5406
|
+
"parent",
|
5407
|
+
""
|
5408
|
+
]
|
5409
|
+
});
|
5410
|
+
prevSiblings[level--] = void 0;
|
5411
|
+
parent = parent.parent;
|
5412
|
+
}
|
5413
|
+
}
|
5414
|
+
});
|
5415
|
+
invariant5(tree, void 0, {
|
5416
|
+
F: __dxlog_file11,
|
5417
|
+
L: 296,
|
5418
|
+
S: void 0,
|
5419
|
+
A: [
|
5420
|
+
"tree",
|
5421
|
+
""
|
5422
|
+
]
|
5423
|
+
});
|
5424
|
+
return tree;
|
5425
|
+
};
|
5426
|
+
return [
|
5427
|
+
StateField9.define({
|
5428
|
+
create: (state) => {
|
5429
|
+
return buildTree(state);
|
5430
|
+
},
|
5431
|
+
update: (value, tr) => {
|
5432
|
+
if (!tr.docChanged) {
|
5433
|
+
return value;
|
5434
|
+
}
|
5435
|
+
return buildTree(tr.state);
|
5436
|
+
},
|
5437
|
+
provide: (field) => treeFacet.from(field)
|
5438
|
+
})
|
5439
|
+
];
|
5440
|
+
};
|
5441
|
+
|
5442
|
+
// packages/ui/react-ui-editor/src/extensions/outliner/selection.ts
|
5443
|
+
var getSelection = (state) => state.selection.main;
|
5444
|
+
var selectionEquals = (a, b) => a.length === b.length && a.every((i) => b.includes(i));
|
5445
|
+
var selectionFacet = Facet3.define({
|
5446
|
+
combine: (values) => values[0]
|
5447
|
+
});
|
5448
|
+
var selectionCompartment = new Compartment();
|
5449
|
+
var selectNone = (view) => {
|
5450
|
+
view.dispatch({
|
5451
|
+
effects: selectionCompartment.reconfigure(selectionFacet.of([]))
|
5452
|
+
});
|
5453
|
+
return true;
|
5454
|
+
};
|
5455
|
+
var selectAll = (view) => {
|
5456
|
+
const tree = view.state.facet(treeFacet);
|
5457
|
+
const selection = view.state.facet(selectionFacet);
|
5458
|
+
const items = [];
|
5459
|
+
tree.traverse((item) => items.push(item.index));
|
5460
|
+
view.dispatch({
|
5461
|
+
effects: selectionCompartment.reconfigure(selectionFacet.of(selectionEquals(selection, items) ? [] : items))
|
5462
|
+
});
|
5463
|
+
return true;
|
5464
|
+
};
|
5465
|
+
var selectUp = (view) => {
|
5466
|
+
return true;
|
5467
|
+
};
|
5468
|
+
var selectDown = (view) => {
|
5469
|
+
return true;
|
5470
|
+
};
|
5471
|
+
|
5472
|
+
// packages/ui/react-ui-editor/src/extensions/outliner/commands.ts
|
5473
|
+
var indentItemMore = (view) => {
|
5474
|
+
const pos = getSelection(view.state).from;
|
5475
|
+
const tree = view.state.facet(treeFacet);
|
5476
|
+
const current = tree.find(pos);
|
5477
|
+
if (current) {
|
5478
|
+
const previous = tree.prev(current);
|
5479
|
+
if (previous && current.level <= previous.level) {
|
5480
|
+
indentMore(view);
|
5481
|
+
}
|
5482
|
+
}
|
5483
|
+
return true;
|
5484
|
+
};
|
5485
|
+
var indentItemLess = (view) => {
|
5486
|
+
const pos = getSelection(view.state).from;
|
5487
|
+
const tree = view.state.facet(treeFacet);
|
5488
|
+
const current = tree.find(pos);
|
5489
|
+
if (current) {
|
5490
|
+
if (current.level > 0) {
|
5491
|
+
const indentUnit = getIndentUnit(view.state);
|
5492
|
+
const changes = [];
|
5493
|
+
tree.traverse(current, (item) => {
|
5494
|
+
const line = view.state.doc.lineAt(item.lineRange.from);
|
5495
|
+
changes.push({
|
5496
|
+
from: line.from,
|
5497
|
+
to: line.from + indentUnit
|
5498
|
+
});
|
5499
|
+
});
|
5500
|
+
if (changes.length > 0) {
|
5501
|
+
view.dispatch({
|
5502
|
+
changes
|
5503
|
+
});
|
5504
|
+
}
|
5505
|
+
}
|
5506
|
+
}
|
5507
|
+
return true;
|
5508
|
+
};
|
5509
|
+
var moveItemDown = (view) => {
|
5510
|
+
const pos = getSelection(view.state)?.from;
|
5511
|
+
const tree = view.state.facet(treeFacet);
|
5512
|
+
const current = tree.find(pos);
|
5513
|
+
if (current && current.nextSibling) {
|
5514
|
+
const next = current.nextSibling;
|
5515
|
+
const currentContent = view.state.doc.sliceString(...getRange(tree, current));
|
5516
|
+
const nextContent = view.state.doc.sliceString(...getRange(tree, next));
|
5517
|
+
const changes = [
|
5518
|
+
{
|
5519
|
+
from: current.lineRange.from,
|
5520
|
+
to: current.lineRange.from + currentContent.length,
|
5521
|
+
insert: nextContent
|
5522
|
+
},
|
5523
|
+
{
|
5524
|
+
from: next.lineRange.from,
|
5525
|
+
to: next.lineRange.from + nextContent.length,
|
5526
|
+
insert: currentContent
|
5527
|
+
}
|
5528
|
+
];
|
5529
|
+
view.dispatch({
|
5530
|
+
changes,
|
5531
|
+
selection: EditorSelection3.cursor(pos + nextContent.length + 1),
|
5532
|
+
scrollIntoView: true
|
5533
|
+
});
|
5534
|
+
}
|
5535
|
+
return true;
|
5536
|
+
};
|
5537
|
+
var moveItemUp = (view) => {
|
5538
|
+
const pos = getSelection(view.state)?.from;
|
5539
|
+
const tree = view.state.facet(treeFacet);
|
5540
|
+
const current = tree.find(pos);
|
5541
|
+
if (current && current.prevSibling) {
|
5542
|
+
const prev = current.prevSibling;
|
5543
|
+
const currentContent = view.state.doc.sliceString(...getRange(tree, current));
|
5544
|
+
const prevContent = view.state.doc.sliceString(...getRange(tree, prev));
|
5545
|
+
const changes = [
|
5546
|
+
{
|
5547
|
+
from: prev.lineRange.from,
|
5548
|
+
to: prev.lineRange.from + prevContent.length,
|
5549
|
+
insert: currentContent
|
5550
|
+
},
|
5551
|
+
{
|
5552
|
+
from: current.lineRange.from,
|
5553
|
+
to: current.lineRange.from + currentContent.length,
|
5554
|
+
insert: prevContent
|
5555
|
+
}
|
5556
|
+
];
|
5557
|
+
view.dispatch({
|
5558
|
+
changes,
|
5559
|
+
selection: EditorSelection3.cursor(pos - prevContent.length - 1),
|
5560
|
+
scrollIntoView: true
|
5561
|
+
});
|
5562
|
+
}
|
5563
|
+
return true;
|
5564
|
+
};
|
5565
|
+
var toggleTask = (view) => {
|
5566
|
+
const pos = getSelection(view.state)?.from;
|
5567
|
+
const tree = view.state.facet(treeFacet);
|
5568
|
+
const current = tree.find(pos);
|
5569
|
+
if (current) {
|
5570
|
+
const type = current.type === "task" ? "bullet" : "task";
|
5571
|
+
const indent = " ".repeat(getIndentUnit(view.state) * current.level);
|
5572
|
+
view.dispatch({
|
5573
|
+
changes: [
|
5574
|
+
{
|
5575
|
+
from: current.lineRange.from,
|
5576
|
+
to: current.contentRange.from,
|
5577
|
+
insert: indent + (type === "task" ? "- [ ] " : "- ")
|
5578
|
+
}
|
5579
|
+
]
|
5580
|
+
});
|
5581
|
+
}
|
5582
|
+
return true;
|
5583
|
+
};
|
5584
|
+
var commands = () => keymap11.of([
|
5585
|
+
//
|
5586
|
+
// Indentation.
|
5587
|
+
//
|
5588
|
+
{
|
5589
|
+
key: "Tab",
|
5590
|
+
preventDefault: true,
|
5591
|
+
run: indentItemMore,
|
5592
|
+
shift: indentItemLess
|
5593
|
+
},
|
5594
|
+
//
|
5595
|
+
// Continuation.
|
5596
|
+
//
|
5597
|
+
{
|
5598
|
+
key: "Enter",
|
5599
|
+
shift: (view) => {
|
5600
|
+
const pos = getSelection(view.state).from;
|
5601
|
+
const insert = "\n ";
|
5602
|
+
view.dispatch({
|
5603
|
+
changes: [
|
5604
|
+
{
|
5605
|
+
from: pos,
|
5606
|
+
to: pos,
|
5607
|
+
insert
|
5608
|
+
}
|
5609
|
+
],
|
5610
|
+
selection: EditorSelection3.cursor(pos + insert.length)
|
5611
|
+
});
|
5612
|
+
return true;
|
5613
|
+
}
|
5614
|
+
},
|
5615
|
+
//
|
5616
|
+
// Navigation.
|
5617
|
+
//
|
5618
|
+
{
|
5619
|
+
key: "ArrowDown",
|
5620
|
+
// Jump to next item (default moves to end of currentline).
|
5621
|
+
run: (view) => {
|
5622
|
+
const tree = view.state.facet(treeFacet);
|
5623
|
+
const item = tree.find(getSelection(view.state).from);
|
5624
|
+
if (item && view.state.doc.lineAt(item.lineRange.to).number - view.state.doc.lineAt(item.lineRange.from).number === 0) {
|
5625
|
+
const next = tree.next(item);
|
5626
|
+
if (next) {
|
5627
|
+
view.dispatch({
|
5628
|
+
selection: EditorSelection3.cursor(next.contentRange.from)
|
5629
|
+
});
|
5630
|
+
return true;
|
5631
|
+
}
|
5632
|
+
}
|
5633
|
+
return false;
|
5634
|
+
}
|
5635
|
+
},
|
5636
|
+
//
|
5637
|
+
// Line selection.
|
5638
|
+
// TODO(burdon): Shortcut to select current item?
|
5639
|
+
//
|
5640
|
+
{
|
5641
|
+
key: "Mod-a",
|
5642
|
+
preventDefault: true,
|
5643
|
+
run: selectAll
|
5644
|
+
},
|
5645
|
+
{
|
5646
|
+
key: "Escape",
|
5647
|
+
preventDefault: true,
|
5648
|
+
run: selectNone
|
5649
|
+
},
|
5650
|
+
{
|
5651
|
+
key: "ArrowUp",
|
5652
|
+
shift: selectUp
|
5653
|
+
},
|
5654
|
+
{
|
5655
|
+
key: "ArrowDown",
|
5656
|
+
shift: selectDown
|
5657
|
+
},
|
5658
|
+
//
|
5659
|
+
// Move.
|
5660
|
+
//
|
5661
|
+
{
|
5662
|
+
key: "Alt-ArrowDown",
|
5663
|
+
preventDefault: true,
|
5664
|
+
run: moveItemDown
|
5665
|
+
},
|
5666
|
+
{
|
5667
|
+
key: "Alt-ArrowUp",
|
5668
|
+
preventDefault: true,
|
5669
|
+
run: moveItemUp
|
5670
|
+
},
|
5671
|
+
//
|
5672
|
+
// Misc.
|
5673
|
+
//
|
5674
|
+
{
|
5675
|
+
key: "Alt-t",
|
5676
|
+
run: toggleTask
|
5677
|
+
}
|
5678
|
+
]);
|
5679
|
+
|
5680
|
+
// packages/ui/react-ui-editor/src/extensions/outliner/editor.ts
|
5681
|
+
import { EditorSelection as EditorSelection4, EditorState as EditorState2 } from "@codemirror/state";
|
5682
|
+
import { ViewPlugin as ViewPlugin11 } from "@codemirror/view";
|
5683
|
+
import { log as log7 } from "@dxos/log";
|
5684
|
+
var __dxlog_file12 = "/home/runner/work/dxos/dxos/packages/ui/react-ui-editor/src/extensions/outliner/editor.ts";
|
5685
|
+
var LIST_ITEM_REGEX = /^\s*- (\[ \]|\[x\])? /;
|
5686
|
+
var initialize = () => {
|
5687
|
+
return ViewPlugin11.fromClass(class {
|
5688
|
+
constructor(view) {
|
5689
|
+
const first = view.state.doc.lineAt(0);
|
5690
|
+
const text = view.state.sliceDoc(first.from, first.to);
|
5691
|
+
const match = text.match(LIST_ITEM_REGEX);
|
5692
|
+
if (!match) {
|
5693
|
+
setTimeout(() => {
|
5694
|
+
const insert = "- [ ] ";
|
5695
|
+
view.dispatch({
|
5696
|
+
changes: [
|
5697
|
+
{
|
5698
|
+
from: 0,
|
5699
|
+
to: 0,
|
5700
|
+
insert
|
5701
|
+
}
|
5702
|
+
],
|
5703
|
+
selection: EditorSelection4.cursor(insert.length)
|
5704
|
+
});
|
5705
|
+
});
|
5706
|
+
}
|
5707
|
+
}
|
4977
5708
|
});
|
4978
5709
|
};
|
4979
|
-
|
4980
|
-
|
4981
|
-
import { syntaxTree as syntaxTree9 } from "@codemirror/language";
|
4982
|
-
import { StateField as StateField10, EditorState as EditorState2 } from "@codemirror/state";
|
4983
|
-
import { Decoration as Decoration8, EditorView as EditorView19 } from "@codemirror/view";
|
4984
|
-
import { log as log6 } from "@dxos/log";
|
4985
|
-
import { mx as mx3 } from "@dxos/react-ui-theme";
|
4986
|
-
var __dxlog_file10 = "/home/runner/work/dxos/dxos/packages/ui/react-ui-editor/src/extensions/markdown/outliner.ts";
|
4987
|
-
var indentLevel = 2;
|
4988
|
-
var matchTaskMarker = /^\s*- (\[ \]|\[x\])? /;
|
4989
|
-
var getLineInfo = (line) => {
|
4990
|
-
const match = line.text.match(matchTaskMarker);
|
4991
|
-
const start = line.from + (match?.[0]?.length ?? 0);
|
4992
|
-
return {
|
4993
|
-
match,
|
4994
|
-
start
|
4995
|
-
};
|
4996
|
-
};
|
4997
|
-
var outliner = () => [
|
5710
|
+
var editor = () => [
|
5711
|
+
initialize(),
|
4998
5712
|
EditorState2.transactionFilter.of((tr) => {
|
5713
|
+
const tree = tr.state.facet(treeFacet);
|
4999
5714
|
if (!tr.docChanged) {
|
5000
|
-
const
|
5001
|
-
if (
|
5002
|
-
const
|
5003
|
-
if (
|
5004
|
-
|
5715
|
+
const current = getSelection(tr.state).from;
|
5716
|
+
if (current != null) {
|
5717
|
+
const currentItem = tree.find(current);
|
5718
|
+
if (!currentItem) {
|
5719
|
+
return [];
|
5720
|
+
}
|
5721
|
+
if (current < currentItem.contentRange.from || current > currentItem.contentRange.to) {
|
5722
|
+
const prev = getSelection(tr.startState).from;
|
5723
|
+
const prevItem = prev != null ? tree.find(prev) : void 0;
|
5724
|
+
if (!prevItem) {
|
5005
5725
|
return [
|
5006
5726
|
{
|
5007
|
-
selection:
|
5008
|
-
anchor: start,
|
5009
|
-
head: start
|
5010
|
-
}
|
5727
|
+
selection: EditorSelection4.cursor(currentItem.contentRange.from)
|
5011
5728
|
}
|
5012
5729
|
];
|
5730
|
+
} else {
|
5731
|
+
if (currentItem.index < prevItem.index) {
|
5732
|
+
return [
|
5733
|
+
{
|
5734
|
+
selection: EditorSelection4.cursor(currentItem.contentRange.to)
|
5735
|
+
}
|
5736
|
+
];
|
5737
|
+
} else if (currentItem.index > prevItem.index) {
|
5738
|
+
return [
|
5739
|
+
{
|
5740
|
+
selection: EditorSelection4.cursor(currentItem.contentRange.from)
|
5741
|
+
}
|
5742
|
+
];
|
5743
|
+
} else {
|
5744
|
+
if (current < prev) {
|
5745
|
+
if (currentItem.index === 0) {
|
5746
|
+
return [];
|
5747
|
+
} else {
|
5748
|
+
return [
|
5749
|
+
{
|
5750
|
+
selection: EditorSelection4.cursor(currentItem.lineRange.from - 1)
|
5751
|
+
}
|
5752
|
+
];
|
5753
|
+
}
|
5754
|
+
} else {
|
5755
|
+
return [
|
5756
|
+
{
|
5757
|
+
selection: EditorSelection4.cursor(currentItem.contentRange.to)
|
5758
|
+
}
|
5759
|
+
];
|
5760
|
+
}
|
5761
|
+
}
|
5013
5762
|
}
|
5014
5763
|
}
|
5015
5764
|
}
|
5016
5765
|
return tr;
|
5017
5766
|
}
|
5767
|
+
let cancel = false;
|
5018
5768
|
const changes = [];
|
5019
5769
|
tr.changes.iterChanges((fromA, toA, fromB, toB, insert) => {
|
5020
5770
|
const line = tr.startState.doc.lineAt(fromA);
|
5021
|
-
const
|
5022
|
-
if (
|
5023
|
-
const
|
5771
|
+
const match = line.text.match(LIST_ITEM_REGEX);
|
5772
|
+
if (match) {
|
5773
|
+
const currentItem = tree.find(tr.state.selection.main.from);
|
5774
|
+
if (!currentItem?.contentRange) {
|
5775
|
+
cancel = true;
|
5776
|
+
return;
|
5777
|
+
}
|
5778
|
+
const start = line.from + (match?.[0]?.length ?? 0);
|
5024
5779
|
const replace = start === toA && toA - fromA === insert.length;
|
5025
5780
|
if (replace) {
|
5026
|
-
log6.info("delete line", void 0, {
|
5027
|
-
F: __dxlog_file10,
|
5028
|
-
L: 82,
|
5029
|
-
S: void 0,
|
5030
|
-
C: (f, a) => f(...a)
|
5031
|
-
});
|
5032
5781
|
changes.push({
|
5033
5782
|
from: line.from - 1,
|
5034
5783
|
to: toA
|
@@ -5040,24 +5789,9 @@ var outliner = () => [
|
|
5040
5789
|
const line2 = tr.state.doc.lineAt(fromA);
|
5041
5790
|
if (line2.text.match(/^\s*$/)) {
|
5042
5791
|
if (line2.from === 0) {
|
5043
|
-
|
5044
|
-
F: __dxlog_file10,
|
5045
|
-
L: 94,
|
5046
|
-
S: void 0,
|
5047
|
-
C: (f, a) => f(...a)
|
5048
|
-
});
|
5049
|
-
changes.push({
|
5050
|
-
from: 0,
|
5051
|
-
to: 0
|
5052
|
-
});
|
5792
|
+
cancel = true;
|
5053
5793
|
return;
|
5054
5794
|
} else {
|
5055
|
-
log6.info("delete line", void 0, {
|
5056
|
-
F: __dxlog_file10,
|
5057
|
-
L: 99,
|
5058
|
-
S: void 0,
|
5059
|
-
C: (f, a) => f(...a)
|
5060
|
-
});
|
5061
5795
|
changes.push({
|
5062
5796
|
from: line2.from - 1,
|
5063
5797
|
to: toA
|
@@ -5068,44 +5802,17 @@ var outliner = () => [
|
|
5068
5802
|
}
|
5069
5803
|
return;
|
5070
5804
|
}
|
5071
|
-
|
5072
|
-
|
5073
|
-
|
5074
|
-
|
5075
|
-
L: 111,
|
5076
|
-
S: void 0,
|
5077
|
-
C: (f, a) => f(...a)
|
5078
|
-
});
|
5079
|
-
changes.push({
|
5080
|
-
from: 0,
|
5081
|
-
to: 0
|
5082
|
-
});
|
5083
|
-
return;
|
5084
|
-
} else {
|
5085
|
-
const getIndent = (text) => (text.match(/^\s*/)?.[0]?.length ?? 0) / indentLevel;
|
5086
|
-
const currentIndent = getIndent(line.text);
|
5087
|
-
const indentPrevious = getIndent(tr.state.doc.lineAt(fromA - 1).text);
|
5088
|
-
if (currentIndent > indentPrevious) {
|
5089
|
-
log6.info("skip", void 0, {
|
5090
|
-
F: __dxlog_file10,
|
5091
|
-
L: 119,
|
5092
|
-
S: void 0,
|
5093
|
-
C: (f, a) => f(...a)
|
5094
|
-
});
|
5095
|
-
changes.push({
|
5096
|
-
from: 0,
|
5097
|
-
to: 0
|
5098
|
-
});
|
5099
|
-
return;
|
5100
|
-
}
|
5101
|
-
}
|
5805
|
+
const item = tree.find(fromA);
|
5806
|
+
if (item?.contentRange.from === item?.contentRange.to && fromA === toA) {
|
5807
|
+
cancel = true;
|
5808
|
+
return;
|
5102
5809
|
}
|
5103
|
-
|
5810
|
+
log7("change", {
|
5811
|
+
item,
|
5104
5812
|
line: {
|
5105
5813
|
from: line.from,
|
5106
5814
|
to: line.to
|
5107
5815
|
},
|
5108
|
-
start,
|
5109
5816
|
a: [
|
5110
5817
|
fromA,
|
5111
5818
|
toA
|
@@ -5119,194 +5826,144 @@ var outliner = () => [
|
|
5119
5826
|
length: insert.length
|
5120
5827
|
}
|
5121
5828
|
}, {
|
5122
|
-
F:
|
5123
|
-
L:
|
5829
|
+
F: __dxlog_file12,
|
5830
|
+
L: 160,
|
5124
5831
|
S: void 0,
|
5125
5832
|
C: (f, a) => f(...a)
|
5126
5833
|
});
|
5127
5834
|
}
|
5128
5835
|
});
|
5129
5836
|
if (changes.length > 0) {
|
5837
|
+
log7("modified,", {
|
5838
|
+
changes
|
5839
|
+
}, {
|
5840
|
+
F: __dxlog_file12,
|
5841
|
+
L: 171,
|
5842
|
+
S: void 0,
|
5843
|
+
C: (f, a) => f(...a)
|
5844
|
+
});
|
5130
5845
|
return [
|
5131
5846
|
{
|
5132
5847
|
changes
|
5133
5848
|
}
|
5134
5849
|
];
|
5850
|
+
} else if (cancel) {
|
5851
|
+
log7("cancel", void 0, {
|
5852
|
+
F: __dxlog_file12,
|
5853
|
+
L: 174,
|
5854
|
+
S: void 0,
|
5855
|
+
C: (f, a) => f(...a)
|
5856
|
+
});
|
5857
|
+
return [];
|
5135
5858
|
}
|
5136
5859
|
return tr;
|
5860
|
+
})
|
5861
|
+
];
|
5862
|
+
|
5863
|
+
// packages/ui/react-ui-editor/src/extensions/outliner/outliner.ts
|
5864
|
+
var outliner = () => [
|
5865
|
+
// Commands.
|
5866
|
+
Prec2.highest(commands()),
|
5867
|
+
// Selection.
|
5868
|
+
selectionCompartment.of(selectionFacet.of([])),
|
5869
|
+
// State.
|
5870
|
+
outlinerTree(),
|
5871
|
+
// Filter and possibly modify changes.
|
5872
|
+
editor(),
|
5873
|
+
// Floating menu.
|
5874
|
+
floatingMenu(),
|
5875
|
+
// Line decorations.
|
5876
|
+
decorations(),
|
5877
|
+
// Default markdown decorations.
|
5878
|
+
decorateMarkdown({
|
5879
|
+
listPaddingLeft: 8
|
5137
5880
|
}),
|
5138
|
-
|
5139
|
-
|
5140
|
-
|
5141
|
-
|
5142
|
-
|
5143
|
-
|
5144
|
-
|
5145
|
-
|
5146
|
-
|
5147
|
-
|
5148
|
-
|
5149
|
-
|
5150
|
-
|
5151
|
-
|
5152
|
-
|
5881
|
+
// Researve space for menu.
|
5882
|
+
EditorView19.contentAttributes.of({
|
5883
|
+
class: "is-full !mr-[3rem]"
|
5884
|
+
})
|
5885
|
+
];
|
5886
|
+
var decorations = () => [
|
5887
|
+
ViewPlugin12.fromClass(class {
|
5888
|
+
constructor(view) {
|
5889
|
+
this.decorations = Decoration9.none;
|
5890
|
+
this.updateDecorations(view.state, view);
|
5891
|
+
}
|
5892
|
+
update(update2) {
|
5893
|
+
const selectionChanged = !selectionEquals(update2.state.facet(selectionFacet), update2.startState.facet(selectionFacet));
|
5894
|
+
if (update2.focusChanged || update2.docChanged || update2.viewportChanged || update2.selectionSet || selectionChanged) {
|
5895
|
+
this.updateDecorations(update2.state, update2.view);
|
5896
|
+
}
|
5897
|
+
}
|
5898
|
+
updateDecorations(state, { viewport: { from, to }, hasFocus }) {
|
5899
|
+
const selection = state.facet(selectionFacet);
|
5900
|
+
const tree = state.facet(treeFacet);
|
5901
|
+
const current = tree.find(state.selection.ranges[state.selection.mainIndex]?.from);
|
5902
|
+
const doc = state.doc;
|
5903
|
+
const decorations2 = [];
|
5904
|
+
for (let lineNum = doc.lineAt(from).number; lineNum <= doc.lineAt(to).number; lineNum++) {
|
5905
|
+
const line = doc.line(lineNum);
|
5906
|
+
const item = tree.find(line.from);
|
5907
|
+
if (item) {
|
5908
|
+
const lineFrom = doc.lineAt(item.contentRange.from);
|
5909
|
+
const lineTo = doc.lineAt(item.contentRange.to);
|
5910
|
+
const isSelected = selection.includes(item.index) || item === current;
|
5911
|
+
decorations2.push(Decoration9.line({
|
5912
|
+
class: mx3("cm-list-item", lineFrom.number === line.number && "cm-list-item-start", lineTo.number === line.number && "cm-list-item-end", isSelected && (hasFocus ? "cm-list-item-focused" : "cm-list-item-selected"))
|
5913
|
+
}).range(line.from, line.from));
|
5914
|
+
}
|
5915
|
+
}
|
5916
|
+
this.decorations = Decoration9.set(decorations2);
|
5917
|
+
}
|
5918
|
+
}, {
|
5919
|
+
decorations: (v) => v.decorations
|
5153
5920
|
}),
|
5154
|
-
//
|
5155
|
-
// TODO(burdon): Hover to select entire group.
|
5921
|
+
// Theme.
|
5156
5922
|
EditorView19.theme({
|
5923
|
+
".cm-list-item": {
|
5924
|
+
borderLeftWidth: "1px",
|
5925
|
+
borderRightWidth: "1px",
|
5926
|
+
paddingLeft: "32px",
|
5927
|
+
borderColor: "transparent"
|
5928
|
+
},
|
5929
|
+
".cm-list-item.cm-codeblock-start": {
|
5930
|
+
borderRadius: "0"
|
5931
|
+
},
|
5157
5932
|
".cm-list-item-start": {
|
5158
|
-
|
5159
|
-
borderLeft: "1px solid var(--dx-separator)",
|
5160
|
-
borderRight: "1px solid var(--dx-separator)",
|
5933
|
+
borderTopWidth: "1px",
|
5161
5934
|
borderTopLeftRadius: "4px",
|
5162
5935
|
borderTopRightRadius: "4px",
|
5163
5936
|
paddingTop: "4px",
|
5164
5937
|
marginTop: "8px"
|
5165
5938
|
},
|
5166
5939
|
".cm-list-item-end": {
|
5167
|
-
|
5168
|
-
borderRight: "1px solid var(--dx-separator)",
|
5169
|
-
borderBottom: "1px solid var(--dx-separator)",
|
5940
|
+
borderBottomWidth: "1px",
|
5170
5941
|
borderBottomLeftRadius: "4px",
|
5171
5942
|
borderBottomRightRadius: "4px",
|
5172
5943
|
paddingBottom: "4px",
|
5173
5944
|
marginBottom: "8px"
|
5174
5945
|
},
|
5175
|
-
".cm-list-item-
|
5176
|
-
|
5177
|
-
borderRight: "1px solid var(--dx-separator)",
|
5178
|
-
// TODO(burdon): Should match parent indentation.
|
5179
|
-
paddingLeft: "24px"
|
5946
|
+
".cm-list-item-selected": {
|
5947
|
+
borderColor: "var(--dx-separator)"
|
5180
5948
|
},
|
5181
|
-
|
5182
|
-
|
5183
|
-
borderRadius: "0"
|
5949
|
+
".cm-list-item-focused": {
|
5950
|
+
borderColor: "var(--dx-accentFocusIndicator)"
|
5184
5951
|
}
|
5185
5952
|
})
|
5186
5953
|
];
|
5187
|
-
var buildDecorations3 = (from, to, state) => {
|
5188
|
-
const decorations = [];
|
5189
|
-
syntaxTree9(state).iterate({
|
5190
|
-
enter: (node) => {
|
5191
|
-
if (node.name === "ListItem") {
|
5192
|
-
const sub = node.node.getChild("BulletList");
|
5193
|
-
const lineStart = state.doc.lineAt(node.from);
|
5194
|
-
const lineEnd = sub ? state.doc.lineAt(state.doc.lineAt(sub.from).from - 1) : state.doc.lineAt(node.to);
|
5195
|
-
decorations.push(Decoration8.line({
|
5196
|
-
class: mx3("cm-list-item-start", lineStart.number === lineEnd.number && "cm-list-item-end")
|
5197
|
-
}).range(lineStart.from, lineStart.from));
|
5198
|
-
for (let i = lineStart.from + 1; i < lineEnd.from; i++) {
|
5199
|
-
decorations.push(Decoration8.line({
|
5200
|
-
class: mx3("cm-list-item-continuation")
|
5201
|
-
}).range(i, i));
|
5202
|
-
}
|
5203
|
-
if (lineStart.number !== lineEnd.number) {
|
5204
|
-
decorations.push(Decoration8.line({
|
5205
|
-
class: mx3("cm-list-item-end")
|
5206
|
-
}).range(lineEnd.from, lineEnd.from));
|
5207
|
-
}
|
5208
|
-
}
|
5209
|
-
}
|
5210
|
-
});
|
5211
|
-
return decorations;
|
5212
|
-
};
|
5213
|
-
|
5214
|
-
// packages/ui/react-ui-editor/src/extensions/mention.ts
|
5215
|
-
import { autocompletion as autocompletion2 } from "@codemirror/autocomplete";
|
5216
|
-
import { log as log7 } from "@dxos/log";
|
5217
|
-
var __dxlog_file11 = "/home/runner/work/dxos/dxos/packages/ui/react-ui-editor/src/extensions/mention.ts";
|
5218
|
-
var mention = ({ debug, onSearch }) => {
|
5219
|
-
return autocompletion2({
|
5220
|
-
// TODO(burdon): Not working.
|
5221
|
-
activateOnTyping: true,
|
5222
|
-
// activateOnTypingDelay: 100,
|
5223
|
-
// selectOnOpen: true,
|
5224
|
-
closeOnBlur: !debug,
|
5225
|
-
// defaultKeymap: false,
|
5226
|
-
icons: false,
|
5227
|
-
override: [
|
5228
|
-
(context) => {
|
5229
|
-
log7.info("completion context", {
|
5230
|
-
context
|
5231
|
-
}, {
|
5232
|
-
F: __dxlog_file11,
|
5233
|
-
L: 27,
|
5234
|
-
S: void 0,
|
5235
|
-
C: (f, a) => f(...a)
|
5236
|
-
});
|
5237
|
-
const match = context.matchBefore(/@(\w+)?/);
|
5238
|
-
if (!match || match.from === match.to && !context.explicit) {
|
5239
|
-
return null;
|
5240
|
-
}
|
5241
|
-
return {
|
5242
|
-
from: match.from,
|
5243
|
-
options: onSearch(match.text.slice(1).toLowerCase()).map((value) => ({
|
5244
|
-
label: `@${value}`
|
5245
|
-
}))
|
5246
|
-
};
|
5247
|
-
}
|
5248
|
-
]
|
5249
|
-
});
|
5250
|
-
};
|
5251
|
-
|
5252
|
-
// packages/ui/react-ui-editor/src/extensions/modes.ts
|
5253
|
-
import { keymap as keymap9 } from "@codemirror/view";
|
5254
|
-
import { vim } from "@replit/codemirror-vim";
|
5255
|
-
import { vscodeKeymap } from "@replit/codemirror-vscode-keymap";
|
5256
|
-
import { Schema } from "effect";
|
5257
|
-
var EditorViewModes = [
|
5258
|
-
"preview",
|
5259
|
-
"readonly",
|
5260
|
-
"source"
|
5261
|
-
];
|
5262
|
-
var EditorViewMode = Schema.Union(...EditorViewModes.map((mode) => Schema.Literal(mode)));
|
5263
|
-
var EditorInputModes = [
|
5264
|
-
"default",
|
5265
|
-
"vim",
|
5266
|
-
"vscode"
|
5267
|
-
];
|
5268
|
-
var EditorInputMode = Schema.Union(...EditorInputModes.map((mode) => Schema.Literal(mode)));
|
5269
|
-
var editorInputMode = singleValueFacet({});
|
5270
|
-
var InputModeExtensions = {
|
5271
|
-
default: [],
|
5272
|
-
vscode: [
|
5273
|
-
// https://github.com/replit/codemirror-vscode-keymap
|
5274
|
-
editorInputMode.of({
|
5275
|
-
type: "vscode"
|
5276
|
-
}),
|
5277
|
-
keymap9.of(vscodeKeymap)
|
5278
|
-
],
|
5279
|
-
vim: [
|
5280
|
-
// https://github.com/replit/codemirror-vim
|
5281
|
-
vim(),
|
5282
|
-
editorInputMode.of({
|
5283
|
-
type: "vim",
|
5284
|
-
noTabster: true
|
5285
|
-
}),
|
5286
|
-
keymap9.of([
|
5287
|
-
{
|
5288
|
-
key: "Alt-Escape",
|
5289
|
-
run: (view) => {
|
5290
|
-
view.dom.parentElement?.focus();
|
5291
|
-
return true;
|
5292
|
-
}
|
5293
|
-
}
|
5294
|
-
])
|
5295
|
-
]
|
5296
|
-
};
|
5297
5954
|
|
5298
5955
|
// packages/ui/react-ui-editor/src/extensions/preview/preview.ts
|
5299
5956
|
import "@dxos/lit-ui/dx-ref-tag.pcss";
|
5300
5957
|
import { syntaxTree as syntaxTree10 } from "@codemirror/language";
|
5301
|
-
import { RangeSetBuilder as
|
5302
|
-
import { Decoration as
|
5958
|
+
import { RangeSetBuilder as RangeSetBuilder6, StateField as StateField10 } from "@codemirror/state";
|
5959
|
+
import { Decoration as Decoration10, EditorView as EditorView20, WidgetType as WidgetType6 } from "@codemirror/view";
|
5303
5960
|
var preview = (options = {}) => {
|
5304
5961
|
return [
|
5305
5962
|
// NOTE: Atomic block decorations must be created from a state field, now a widget, otherwise it results in the following error:
|
5306
5963
|
// "Block decorations may not be specified via plugins"
|
5307
|
-
|
5308
|
-
create: (state) =>
|
5309
|
-
update: (_, tr) =>
|
5964
|
+
StateField10.define({
|
5965
|
+
create: (state) => buildDecorations3(state, options),
|
5966
|
+
update: (_, tr) => buildDecorations3(tr.state, options),
|
5310
5967
|
provide: (field) => [
|
5311
5968
|
EditorView20.decorations.from(field),
|
5312
5969
|
EditorView20.atomicRanges.of((view) => view.state.field(field))
|
@@ -5337,8 +5994,8 @@ var getLinkRef = (state, node) => {
|
|
5337
5994
|
};
|
5338
5995
|
}
|
5339
5996
|
};
|
5340
|
-
var
|
5341
|
-
const builder = new
|
5997
|
+
var buildDecorations3 = (state, options) => {
|
5998
|
+
const builder = new RangeSetBuilder6();
|
5342
5999
|
syntaxTree10(state).iterate({
|
5343
6000
|
enter: (node) => {
|
5344
6001
|
switch (node.name) {
|
@@ -5349,7 +6006,7 @@ var buildDecorations4 = (state, options) => {
|
|
5349
6006
|
case "Link": {
|
5350
6007
|
const link = getLinkRef(state, node.node);
|
5351
6008
|
if (link) {
|
5352
|
-
builder.add(node.from, node.to,
|
6009
|
+
builder.add(node.from, node.to, Decoration10.replace({
|
5353
6010
|
widget: new PreviewInlineWidget(options, link)
|
5354
6011
|
}));
|
5355
6012
|
}
|
@@ -5362,7 +6019,7 @@ var buildDecorations4 = (state, options) => {
|
|
5362
6019
|
case "Image": {
|
5363
6020
|
const link = getLinkRef(state, node.node);
|
5364
6021
|
if (options.renderBlock && link) {
|
5365
|
-
builder.add(node.from, node.to,
|
6022
|
+
builder.add(node.from, node.to, Decoration10.replace({
|
5366
6023
|
block: true,
|
5367
6024
|
// atomic: true,
|
5368
6025
|
widget: new PreviewBlockWidget(options, link)
|
@@ -5377,9 +6034,7 @@ var buildDecorations4 = (state, options) => {
|
|
5377
6034
|
};
|
5378
6035
|
var PreviewInlineWidget = class extends WidgetType6 {
|
5379
6036
|
constructor(_options, _link) {
|
5380
|
-
super();
|
5381
|
-
this._options = _options;
|
5382
|
-
this._link = _link;
|
6037
|
+
super(), this._options = _options, this._link = _link;
|
5383
6038
|
}
|
5384
6039
|
// override ignoreEvent() {
|
5385
6040
|
// return false;
|
@@ -5390,15 +6045,13 @@ var PreviewInlineWidget = class extends WidgetType6 {
|
|
5390
6045
|
toDOM(view) {
|
5391
6046
|
const root = document.createElement("dx-ref-tag");
|
5392
6047
|
root.textContent = this._link.label;
|
5393
|
-
root.setAttribute("
|
6048
|
+
root.setAttribute("refId", this._link.ref);
|
5394
6049
|
return root;
|
5395
6050
|
}
|
5396
6051
|
};
|
5397
6052
|
var PreviewBlockWidget = class extends WidgetType6 {
|
5398
6053
|
constructor(_options, _link) {
|
5399
|
-
super();
|
5400
|
-
this._options = _options;
|
5401
|
-
this._link = _link;
|
6054
|
+
super(), this._options = _options, this._link = _link;
|
5402
6055
|
}
|
5403
6056
|
// override ignoreEvent() {
|
5404
6057
|
// return true;
|
@@ -5455,7 +6108,7 @@ var PreviewBlockWidget = class extends WidgetType6 {
|
|
5455
6108
|
};
|
5456
6109
|
|
5457
6110
|
// packages/ui/react-ui-editor/src/extensions/typewriter.ts
|
5458
|
-
import { keymap as
|
6111
|
+
import { keymap as keymap12 } from "@codemirror/view";
|
5459
6112
|
var defaultItems = [
|
5460
6113
|
"hello world!",
|
5461
6114
|
"this is a test.",
|
@@ -5465,7 +6118,7 @@ var typewriter = ({ delay = 75, items = defaultItems } = {}) => {
|
|
5465
6118
|
let t;
|
5466
6119
|
let idx = 0;
|
5467
6120
|
return [
|
5468
|
-
|
6121
|
+
keymap12.of([
|
5469
6122
|
{
|
5470
6123
|
// Reset.
|
5471
6124
|
key: "alt-meta-'",
|
@@ -5569,30 +6222,6 @@ var createBlocks = (state, getView) => {
|
|
5569
6222
|
};
|
5570
6223
|
};
|
5571
6224
|
|
5572
|
-
// packages/ui/react-ui-editor/src/components/EditorToolbar/comment.ts
|
5573
|
-
var commentLabel = (comment, selection) => comment ? "selection overlaps existing comment label" : selection === false ? "select text to comment label" : "comment label";
|
5574
|
-
var createCommentAction = (label, getView) => createEditorAction("comment", () => createComment(getView()), {
|
5575
|
-
testId: "editor.toolbar.comment",
|
5576
|
-
icon: "ph--chat-text--regular",
|
5577
|
-
label
|
5578
|
-
});
|
5579
|
-
var createComment2 = (state, getView) => ({
|
5580
|
-
nodes: [
|
5581
|
-
createCommentAction([
|
5582
|
-
commentLabel(state.comment, state.selection),
|
5583
|
-
{
|
5584
|
-
ns: translationKey
|
5585
|
-
}
|
5586
|
-
], getView)
|
5587
|
-
],
|
5588
|
-
edges: [
|
5589
|
-
{
|
5590
|
-
source: "root",
|
5591
|
-
target: "comment"
|
5592
|
-
}
|
5593
|
-
]
|
5594
|
-
});
|
5595
|
-
|
5596
6225
|
// packages/ui/react-ui-editor/src/components/EditorToolbar/formatting.ts
|
5597
6226
|
var formats = {
|
5598
6227
|
strong: "ph--text-b--regular",
|
@@ -5835,15 +6464,17 @@ var createViewMode = (state, onViewModeChange) => {
|
|
5835
6464
|
// packages/ui/react-ui-editor/src/defaults.ts
|
5836
6465
|
import { EditorView as EditorView21 } from "@codemirror/view";
|
5837
6466
|
import { mx as mx4 } from "@dxos/react-ui-theme";
|
5838
|
-
var margin = "!mt-[1rem]";
|
5839
6467
|
var editorWidth = "!mli-auto is-full max-is-[min(50rem,100%-4rem)]";
|
5840
|
-
var
|
5841
|
-
|
6468
|
+
var editorSlots = {
|
6469
|
+
scroll: {
|
6470
|
+
className: "pbs-2"
|
6471
|
+
},
|
6472
|
+
content: {
|
6473
|
+
className: editorWidth
|
6474
|
+
}
|
6475
|
+
};
|
5842
6476
|
var editorGutter = EditorView21.theme({
|
5843
|
-
// Match margin from content.
|
5844
|
-
// Gutter = 2rem + 1rem margin.
|
5845
6477
|
".cm-gutters": {
|
5846
|
-
marginTop: "1rem",
|
5847
6478
|
paddingRight: "1rem"
|
5848
6479
|
}
|
5849
6480
|
});
|
@@ -5854,104 +6485,264 @@ var editorMonospace = EditorView21.theme({
|
|
5854
6485
|
});
|
5855
6486
|
var editorWithToolbarLayout = "grid grid-cols-1 grid-rows-[min-content_1fr] data-[toolbar=disabled]:grid-rows-[1fr] justify-center content-start overflow-hidden";
|
5856
6487
|
var stackItemContentEditorClassNames = (role) => mx4("attention-surface dx-focus-ring-inset data-[toolbar=disabled]:pbs-2", role === "section" ? "[&_.cm-scroller]:overflow-hidden [&_.cm-scroller]:min-bs-24" : "min-bs-0");
|
5857
|
-
var stackItemContentToolbarClassNames = (role) => mx4("relative z-[1] flex is-full bg-toolbarSurface border-be border-
|
6488
|
+
var stackItemContentToolbarClassNames = (role) => mx4("relative z-[1] flex is-full bg-toolbarSurface border-be border-subduedSeparator", role === "section" && "sticky block-start-0 -mbe-px min-is-0");
|
5858
6489
|
|
5859
6490
|
// packages/ui/react-ui-editor/src/components/EditorToolbar/EditorToolbar.tsx
|
5860
6491
|
var createToolbar = ({ getView, state, customActions, ...features }) => {
|
5861
|
-
|
5862
|
-
|
5863
|
-
|
5864
|
-
|
5865
|
-
|
5866
|
-
|
5867
|
-
|
5868
|
-
|
5869
|
-
|
5870
|
-
|
5871
|
-
|
5872
|
-
|
5873
|
-
|
5874
|
-
|
5875
|
-
|
5876
|
-
|
5877
|
-
|
5878
|
-
|
5879
|
-
|
5880
|
-
|
5881
|
-
|
5882
|
-
|
5883
|
-
|
5884
|
-
|
5885
|
-
|
5886
|
-
|
5887
|
-
|
5888
|
-
|
5889
|
-
const
|
5890
|
-
nodes.push(...
|
5891
|
-
edges.push(...
|
5892
|
-
|
5893
|
-
|
5894
|
-
|
5895
|
-
|
5896
|
-
|
5897
|
-
|
5898
|
-
|
5899
|
-
|
5900
|
-
|
5901
|
-
|
5902
|
-
|
5903
|
-
|
5904
|
-
|
5905
|
-
|
5906
|
-
|
5907
|
-
|
5908
|
-
|
5909
|
-
|
5910
|
-
|
5911
|
-
|
5912
|
-
nodes,
|
5913
|
-
edges
|
5914
|
-
};
|
6492
|
+
return Rx.make((get2) => {
|
6493
|
+
const nodes = [];
|
6494
|
+
const edges = [];
|
6495
|
+
if (features.headings ?? true) {
|
6496
|
+
const headings2 = get2(rxFromSignal(() => createHeadings(state, getView)));
|
6497
|
+
nodes.push(...headings2.nodes);
|
6498
|
+
edges.push(...headings2.edges);
|
6499
|
+
}
|
6500
|
+
if (features.formatting ?? true) {
|
6501
|
+
const formatting = get2(rxFromSignal(() => createFormatting(state, getView)));
|
6502
|
+
nodes.push(...formatting.nodes);
|
6503
|
+
edges.push(...formatting.edges);
|
6504
|
+
}
|
6505
|
+
if (features.lists ?? true) {
|
6506
|
+
const lists = get2(rxFromSignal(() => createLists(state, getView)));
|
6507
|
+
nodes.push(...lists.nodes);
|
6508
|
+
edges.push(...lists.edges);
|
6509
|
+
}
|
6510
|
+
if (features.blocks ?? true) {
|
6511
|
+
const blocks = get2(rxFromSignal(() => createBlocks(state, getView)));
|
6512
|
+
nodes.push(...blocks.nodes);
|
6513
|
+
edges.push(...blocks.edges);
|
6514
|
+
}
|
6515
|
+
if (features.image) {
|
6516
|
+
const image2 = get2(rxFromSignal(() => createImageUpload(features.image)));
|
6517
|
+
nodes.push(...image2.nodes);
|
6518
|
+
edges.push(...image2.edges);
|
6519
|
+
}
|
6520
|
+
const editorToolbarGap = createGapSeparator();
|
6521
|
+
nodes.push(...editorToolbarGap.nodes);
|
6522
|
+
edges.push(...editorToolbarGap.edges);
|
6523
|
+
if (customActions) {
|
6524
|
+
const custom = get2(customActions);
|
6525
|
+
nodes.push(...custom.nodes);
|
6526
|
+
edges.push(...custom.edges);
|
6527
|
+
}
|
6528
|
+
if (features.search ?? true) {
|
6529
|
+
const search = get2(rxFromSignal(() => createSearch(getView)));
|
6530
|
+
nodes.push(...search.nodes);
|
6531
|
+
edges.push(...search.edges);
|
6532
|
+
}
|
6533
|
+
if (features.viewMode) {
|
6534
|
+
const viewMode = get2(rxFromSignal(() => createViewMode(state, features.viewMode)));
|
6535
|
+
nodes.push(...viewMode.nodes);
|
6536
|
+
edges.push(...viewMode.edges);
|
6537
|
+
}
|
6538
|
+
return {
|
6539
|
+
nodes,
|
6540
|
+
edges
|
6541
|
+
};
|
6542
|
+
});
|
5915
6543
|
};
|
5916
6544
|
var useEditorToolbarActionGraph = (props) => {
|
5917
|
-
const menuCreator =
|
5918
|
-
props
|
6545
|
+
const menuCreator = useMemo3(() => createToolbar({
|
6546
|
+
getView: props.getView,
|
6547
|
+
state: props.state,
|
6548
|
+
customActions: props.customActions,
|
6549
|
+
headings: props.headings,
|
6550
|
+
formatting: props.formatting,
|
6551
|
+
lists: props.lists,
|
6552
|
+
blocks: props.blocks,
|
6553
|
+
image: props.image,
|
6554
|
+
search: props.search,
|
6555
|
+
viewMode: props.viewMode
|
6556
|
+
}), [
|
6557
|
+
props.getView,
|
6558
|
+
props.state,
|
6559
|
+
props.customActions,
|
6560
|
+
props.headings,
|
6561
|
+
props.formatting,
|
6562
|
+
props.lists,
|
6563
|
+
props.blocks,
|
6564
|
+
props.image,
|
6565
|
+
props.search,
|
6566
|
+
props.viewMode
|
5919
6567
|
]);
|
5920
6568
|
return useMenuActions(menuCreator);
|
5921
6569
|
};
|
5922
6570
|
var EditorToolbar = /* @__PURE__ */ memo(({ classNames, attendableId, role, ...props }) => {
|
5923
|
-
|
5924
|
-
|
5925
|
-
|
5926
|
-
|
5927
|
-
|
5928
|
-
|
5929
|
-
|
5930
|
-
|
5931
|
-
|
5932
|
-
|
5933
|
-
|
5934
|
-
|
5935
|
-
classNames
|
5936
|
-
|
5937
|
-
|
6571
|
+
var _effect = _useSignals();
|
6572
|
+
try {
|
6573
|
+
const menuProps = useEditorToolbarActionGraph(props);
|
6574
|
+
return /* @__PURE__ */ React3.createElement("div", {
|
6575
|
+
role: "none",
|
6576
|
+
className: stackItemContentToolbarClassNames(role)
|
6577
|
+
}, /* @__PURE__ */ React3.createElement(ElevationProvider, {
|
6578
|
+
elevation: role === "section" ? "positioned" : "base"
|
6579
|
+
}, /* @__PURE__ */ React3.createElement(MenuProvider, {
|
6580
|
+
...menuProps,
|
6581
|
+
attendableId
|
6582
|
+
}, /* @__PURE__ */ React3.createElement(ToolbarMenu, {
|
6583
|
+
classNames: [
|
6584
|
+
textBlockWidth,
|
6585
|
+
classNames
|
6586
|
+
]
|
6587
|
+
}))));
|
6588
|
+
} finally {
|
6589
|
+
_effect.f();
|
6590
|
+
}
|
5938
6591
|
});
|
5939
6592
|
|
6593
|
+
// packages/ui/react-ui-editor/src/components/Popover/RefPopover.tsx
|
6594
|
+
import { useSignals as _useSignals2 } from "@preact-signals/safe-react/tracking";
|
6595
|
+
import { createContext } from "@radix-ui/react-context";
|
6596
|
+
import React4, { useRef, useState, useEffect as useEffect2, useCallback } from "react";
|
6597
|
+
import { addEventListener } from "@dxos/async";
|
6598
|
+
import { Popover } from "@dxos/react-ui";
|
6599
|
+
var customEventOptions = {
|
6600
|
+
capture: true,
|
6601
|
+
passive: false
|
6602
|
+
};
|
6603
|
+
var REF_POPOVER = "RefPopover";
|
6604
|
+
var [RefPopoverContextProvider, useRefPopover] = createContext(REF_POPOVER, {});
|
6605
|
+
var RefPopoverProvider = ({ children, onLookup }) => {
|
6606
|
+
var _effect = _useSignals2();
|
6607
|
+
try {
|
6608
|
+
const trigger = useRef(null);
|
6609
|
+
const [value, setValue] = useState({});
|
6610
|
+
const [rootRef, setRootRef] = useState(null);
|
6611
|
+
const [open, setOpen] = useState(false);
|
6612
|
+
const handleDxRefTagActivate = useCallback((event) => {
|
6613
|
+
const { refId, label, trigger: dxTrigger } = event;
|
6614
|
+
setValue((value2) => ({
|
6615
|
+
...value2,
|
6616
|
+
link: {
|
6617
|
+
label,
|
6618
|
+
ref: refId
|
6619
|
+
},
|
6620
|
+
pending: true
|
6621
|
+
}));
|
6622
|
+
trigger.current = dxTrigger;
|
6623
|
+
queueMicrotask(() => setOpen(true));
|
6624
|
+
void onLookup?.({
|
6625
|
+
label,
|
6626
|
+
ref: refId
|
6627
|
+
}).then((target) => setValue((value2) => ({
|
6628
|
+
...value2,
|
6629
|
+
target: target ?? void 0,
|
6630
|
+
pending: false
|
6631
|
+
})));
|
6632
|
+
}, [
|
6633
|
+
onLookup
|
6634
|
+
]);
|
6635
|
+
useEffect2(() => {
|
6636
|
+
return rootRef ? addEventListener(rootRef, "dx-ref-tag-activate", handleDxRefTagActivate, customEventOptions) : void 0;
|
6637
|
+
}, [
|
6638
|
+
rootRef
|
6639
|
+
]);
|
6640
|
+
return /* @__PURE__ */ React4.createElement(RefPopoverContextProvider, {
|
6641
|
+
pending: value.pending,
|
6642
|
+
link: value.link,
|
6643
|
+
target: value.target
|
6644
|
+
}, /* @__PURE__ */ React4.createElement(Popover.Root, {
|
6645
|
+
open,
|
6646
|
+
onOpenChange: setOpen
|
6647
|
+
}, /* @__PURE__ */ React4.createElement(Popover.VirtualTrigger, {
|
6648
|
+
virtualRef: trigger
|
6649
|
+
}), /* @__PURE__ */ React4.createElement("div", {
|
6650
|
+
role: "none",
|
6651
|
+
className: "contents",
|
6652
|
+
ref: setRootRef
|
6653
|
+
}, children)));
|
6654
|
+
} finally {
|
6655
|
+
_effect.f();
|
6656
|
+
}
|
6657
|
+
};
|
6658
|
+
var RefPopover = {
|
6659
|
+
Provider: RefPopoverProvider
|
6660
|
+
};
|
6661
|
+
|
6662
|
+
// packages/ui/react-ui-editor/src/components/Popover/RefDropdownMenu.tsx
|
6663
|
+
import { useSignals as _useSignals3 } from "@preact-signals/safe-react/tracking";
|
6664
|
+
import { createContext as createContext2 } from "@radix-ui/react-context";
|
6665
|
+
import React5, { useRef as useRef2, useState as useState2, useEffect as useEffect3, useCallback as useCallback2 } from "react";
|
6666
|
+
import { addEventListener as addEventListener2 } from "@dxos/async";
|
6667
|
+
import { DropdownMenu } from "@dxos/react-ui";
|
6668
|
+
var customEventOptions2 = {
|
6669
|
+
capture: true,
|
6670
|
+
passive: false
|
6671
|
+
};
|
6672
|
+
var REF_DROPDOWN_MENU = "RefDropdownMenu";
|
6673
|
+
var [RefDropdownMenuContextProvider, useRefDropdownMenu] = createContext2(REF_DROPDOWN_MENU, {});
|
6674
|
+
var RefDropdownMenuProvider = ({ children, onLookup }) => {
|
6675
|
+
var _effect = _useSignals3();
|
6676
|
+
try {
|
6677
|
+
const trigger = useRef2(null);
|
6678
|
+
const [value, setValue] = useState2({});
|
6679
|
+
const [rootRef, setRootRef] = useState2(null);
|
6680
|
+
const [open, setOpen] = useState2(false);
|
6681
|
+
const handleDxRefTagActivate = useCallback2((event) => {
|
6682
|
+
const { refId, label, trigger: dxTrigger } = event;
|
6683
|
+
setValue((value2) => ({
|
6684
|
+
...value2,
|
6685
|
+
link: {
|
6686
|
+
label,
|
6687
|
+
ref: refId
|
6688
|
+
},
|
6689
|
+
pending: true
|
6690
|
+
}));
|
6691
|
+
trigger.current = dxTrigger;
|
6692
|
+
queueMicrotask(() => setOpen(true));
|
6693
|
+
void onLookup?.({
|
6694
|
+
label,
|
6695
|
+
ref: refId
|
6696
|
+
}).then((target) => setValue((value2) => ({
|
6697
|
+
...value2,
|
6698
|
+
target: target ?? void 0,
|
6699
|
+
pending: false
|
6700
|
+
})));
|
6701
|
+
}, [
|
6702
|
+
onLookup
|
6703
|
+
]);
|
6704
|
+
useEffect3(() => {
|
6705
|
+
return rootRef ? addEventListener2(rootRef, "dx-ref-tag-activate", handleDxRefTagActivate, customEventOptions2) : void 0;
|
6706
|
+
}, [
|
6707
|
+
rootRef
|
6708
|
+
]);
|
6709
|
+
return /* @__PURE__ */ React5.createElement(RefDropdownMenuContextProvider, {
|
6710
|
+
pending: value.pending,
|
6711
|
+
link: value.link,
|
6712
|
+
target: value.target
|
6713
|
+
}, /* @__PURE__ */ React5.createElement(DropdownMenu.Root, {
|
6714
|
+
open,
|
6715
|
+
onOpenChange: setOpen
|
6716
|
+
}, /* @__PURE__ */ React5.createElement(DropdownMenu.VirtualTrigger, {
|
6717
|
+
virtualRef: trigger
|
6718
|
+
}), /* @__PURE__ */ React5.createElement("div", {
|
6719
|
+
role: "none",
|
6720
|
+
className: "contents",
|
6721
|
+
ref: setRootRef
|
6722
|
+
}, children)));
|
6723
|
+
} finally {
|
6724
|
+
_effect.f();
|
6725
|
+
}
|
6726
|
+
};
|
6727
|
+
var RefDropdownMenu = {
|
6728
|
+
Provider: RefDropdownMenuProvider
|
6729
|
+
};
|
6730
|
+
|
5940
6731
|
// packages/ui/react-ui-editor/src/hooks/useTextEditor.ts
|
5941
6732
|
import { EditorState as EditorState3 } from "@codemirror/state";
|
5942
6733
|
import { EditorView as EditorView22 } from "@codemirror/view";
|
5943
6734
|
import { useFocusableGroup } from "@fluentui/react-tabster";
|
5944
|
-
import { useCallback as
|
6735
|
+
import { useCallback as useCallback3, useEffect as useEffect4, useMemo as useMemo4, useRef as useRef3, useState as useState3 } from "react";
|
5945
6736
|
import { log as log8 } from "@dxos/log";
|
5946
6737
|
import { getProviderValue, isNotFalsy as isNotFalsy4 } from "@dxos/util";
|
5947
|
-
var
|
6738
|
+
var __dxlog_file13 = "/home/runner/work/dxos/dxos/packages/ui/react-ui-editor/src/hooks/useTextEditor.ts";
|
5948
6739
|
var instanceCount = 0;
|
5949
6740
|
var useTextEditor = (props = {}, deps = []) => {
|
5950
6741
|
const { id, doc, initialValue, extensions, autoFocus, scrollTo, selection, moveToEndOfLine, debug } = useMemo4(() => getProviderValue(props), deps ?? []);
|
5951
|
-
const [instanceId] =
|
5952
|
-
const [view, setView] =
|
5953
|
-
const parentRef =
|
5954
|
-
|
6742
|
+
const [instanceId] = useState3(() => `text-editor-${++instanceCount}`);
|
6743
|
+
const [view, setView] = useState3();
|
6744
|
+
const parentRef = useRef3(null);
|
6745
|
+
useEffect4(() => {
|
5955
6746
|
let view2;
|
5956
6747
|
if (parentRef.current) {
|
5957
6748
|
log8("create", {
|
@@ -5959,7 +6750,7 @@ var useTextEditor = (props = {}, deps = []) => {
|
|
5959
6750
|
instanceId,
|
5960
6751
|
doc: initialValue?.length ?? 0
|
5961
6752
|
}, {
|
5962
|
-
F:
|
6753
|
+
F: __dxlog_file13,
|
5963
6754
|
L: 76,
|
5964
6755
|
S: void 0,
|
5965
6756
|
C: (f, a) => f(...a)
|
@@ -5985,7 +6776,7 @@ var useTextEditor = (props = {}, deps = []) => {
|
|
5985
6776
|
// NOTE: This doesn't catch errors in keymap functions.
|
5986
6777
|
EditorView22.exceptionSink.of((err) => {
|
5987
6778
|
log8.catch(err, void 0, {
|
5988
|
-
F:
|
6779
|
+
F: __dxlog_file13,
|
5989
6780
|
L: 98,
|
5990
6781
|
S: void 0,
|
5991
6782
|
C: (f, a) => f(...a)
|
@@ -6017,7 +6808,7 @@ var useTextEditor = (props = {}, deps = []) => {
|
|
6017
6808
|
log8("destroy", {
|
6018
6809
|
id
|
6019
6810
|
}, {
|
6020
|
-
F:
|
6811
|
+
F: __dxlog_file13,
|
6021
6812
|
L: 135,
|
6022
6813
|
S: void 0,
|
6023
6814
|
C: (f, a) => f(...a)
|
@@ -6025,7 +6816,7 @@ var useTextEditor = (props = {}, deps = []) => {
|
|
6025
6816
|
view2?.destroy();
|
6026
6817
|
};
|
6027
6818
|
}, deps);
|
6028
|
-
|
6819
|
+
useEffect4(() => {
|
6029
6820
|
if (view) {
|
6030
6821
|
if (scrollTo || selection) {
|
6031
6822
|
if (selection && selection.anchor > view.state.doc.length) {
|
@@ -6034,7 +6825,7 @@ var useTextEditor = (props = {}, deps = []) => {
|
|
6034
6825
|
scrollTo,
|
6035
6826
|
selection
|
6036
6827
|
}, {
|
6037
|
-
F:
|
6828
|
+
F: __dxlog_file13,
|
6038
6829
|
L: 144,
|
6039
6830
|
S: void 0,
|
6040
6831
|
C: (f, a) => f(...a)
|
@@ -6052,7 +6843,7 @@ var useTextEditor = (props = {}, deps = []) => {
|
|
6052
6843
|
scrollTo,
|
6053
6844
|
selection
|
6054
6845
|
]);
|
6055
|
-
|
6846
|
+
useEffect4(() => {
|
6056
6847
|
if (view && autoFocus) {
|
6057
6848
|
view.focus();
|
6058
6849
|
}
|
@@ -6066,7 +6857,7 @@ var useTextEditor = (props = {}, deps = []) => {
|
|
6066
6857
|
Escape: view?.state.facet(editorInputMode).noTabster
|
6067
6858
|
}
|
6068
6859
|
});
|
6069
|
-
const handleKeyUp =
|
6860
|
+
const handleKeyUp = useCallback3((event) => {
|
6070
6861
|
const { key, target, currentTarget } = event;
|
6071
6862
|
if (target === currentTarget) {
|
6072
6863
|
switch (key) {
|
@@ -6101,9 +6892,12 @@ export {
|
|
6101
6892
|
Inline,
|
6102
6893
|
InputModeExtensions,
|
6103
6894
|
List,
|
6895
|
+
RefDropdownMenu,
|
6896
|
+
RefPopover,
|
6104
6897
|
RemoteSelectionsDecorator,
|
6105
6898
|
SpaceAwarenessProvider,
|
6106
6899
|
TextKind,
|
6900
|
+
Tree,
|
6107
6901
|
addBlockquote,
|
6108
6902
|
addCodeblock,
|
6109
6903
|
addLink,
|
@@ -6121,6 +6915,7 @@ export {
|
|
6121
6915
|
closeEffect,
|
6122
6916
|
command,
|
6123
6917
|
commandKeyBindings,
|
6918
|
+
commentClickedEffect,
|
6124
6919
|
comments,
|
6125
6920
|
commentsState,
|
6126
6921
|
convertTreeToJson,
|
@@ -6133,6 +6928,7 @@ export {
|
|
6133
6928
|
createEditorStateTransaction,
|
6134
6929
|
createElement,
|
6135
6930
|
createExternalCommentSync,
|
6931
|
+
createJsonExtensions,
|
6136
6932
|
createMarkdownExtensions,
|
6137
6933
|
createRenderer,
|
6138
6934
|
createThemeExtensions,
|
@@ -6143,33 +6939,39 @@ export {
|
|
6143
6939
|
defaultOptions,
|
6144
6940
|
documentId,
|
6145
6941
|
dropFile,
|
6146
|
-
editorContent,
|
6147
|
-
editorFullWidth,
|
6148
6942
|
editorGutter,
|
6149
6943
|
editorInputMode,
|
6150
6944
|
editorMonospace,
|
6945
|
+
editorSlots,
|
6151
6946
|
editorWidth,
|
6152
6947
|
editorWithToolbarLayout,
|
6153
6948
|
flattenRect,
|
6949
|
+
floatingMenu,
|
6154
6950
|
focus,
|
6155
6951
|
focusField,
|
6156
6952
|
folding,
|
6157
6953
|
formattingEquals,
|
6158
6954
|
formattingKeymap,
|
6159
6955
|
getFormatting,
|
6956
|
+
getListItemContent,
|
6957
|
+
getRange,
|
6160
6958
|
image,
|
6161
6959
|
insertTable,
|
6162
|
-
|
6960
|
+
itemToJSON,
|
6961
|
+
keymap13 as keymap,
|
6163
6962
|
linkTooltip,
|
6963
|
+
listItemToString,
|
6164
6964
|
listener,
|
6165
6965
|
logChanges,
|
6166
6966
|
markdownHighlightStyle,
|
6167
6967
|
markdownTags,
|
6168
6968
|
markdownTagsExtensions,
|
6969
|
+
matchCompletion,
|
6169
6970
|
mention,
|
6170
6971
|
openCommand,
|
6171
6972
|
openEffect,
|
6172
6973
|
outliner,
|
6974
|
+
outlinerTree,
|
6173
6975
|
overlap,
|
6174
6976
|
preventNewline,
|
6175
6977
|
preview,
|
@@ -6181,7 +6983,6 @@ export {
|
|
6181
6983
|
removeStyle,
|
6182
6984
|
renderRoot,
|
6183
6985
|
scrollThreadIntoView,
|
6184
|
-
selectionOverlapsComment,
|
6185
6986
|
selectionState,
|
6186
6987
|
setBlockquote,
|
6187
6988
|
setComments,
|
@@ -6191,6 +6992,7 @@ export {
|
|
6191
6992
|
singleValueFacet,
|
6192
6993
|
stackItemContentEditorClassNames,
|
6193
6994
|
stackItemContentToolbarClassNames,
|
6995
|
+
staticCompletion,
|
6194
6996
|
table,
|
6195
6997
|
tags2 as tags,
|
6196
6998
|
textRange,
|
@@ -6203,12 +7005,15 @@ export {
|
|
6203
7005
|
toggleStrong,
|
6204
7006
|
toggleStyle,
|
6205
7007
|
translations_default as translations,
|
7008
|
+
traverse,
|
7009
|
+
treeFacet,
|
7010
|
+
typeahead,
|
6206
7011
|
typewriter,
|
6207
|
-
useCommentClickListener,
|
6208
|
-
useCommentState,
|
6209
7012
|
useComments,
|
6210
7013
|
useEditorToolbarState,
|
6211
7014
|
useFormattingState,
|
7015
|
+
useRefDropdownMenu,
|
7016
|
+
useRefPopover,
|
6212
7017
|
useTextEditor,
|
6213
7018
|
wrapWithCatch
|
6214
7019
|
};
|